// Copyright (c) 2012 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 "chrome/browser/extensions/extension_sync_data.h"

#include "base/files/file_path.h"
#include "base/memory/scoped_ptr.h"
#include "base/version.h"
#include "extensions/common/extension.h"
#include "sync/api/string_ordinal.h"
#include "sync/protocol/app_specifics.pb.h"
#include "sync/protocol/extension_specifics.pb.h"
#include "sync/protocol/sync.pb.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "url/gurl.h"

namespace extensions {

namespace {

const char kValidId[] = "abcdefghijklmnopabcdefghijklmnop";
const char kVersion[] = "1.0.0.1";
const char kValidUpdateUrl[] =
    "https://clients2.google.com/service/update2/crx";
const int kValidDisableReasons = Extension::DISABLE_USER_ACTION;
const char kName[] = "MyExtension";

// Serializes a protobuf structure (entity specifics) into an ExtensionSyncData
// and back again, and confirms that the input is the same as the output.
void ProtobufToSyncDataEqual(const sync_pb::EntitySpecifics& entity) {
  syncer::SyncData sync_data =
      syncer::SyncData::CreateLocalData("sync_tag", "non_unique_title", entity);
  scoped_ptr<ExtensionSyncData> extension_sync_data =
      ExtensionSyncData::CreateFromSyncData(sync_data);
  ASSERT_TRUE(extension_sync_data.get());
  syncer::SyncData output_sync_data = extension_sync_data->GetSyncData();
  const sync_pb::ExtensionSpecifics& output =
      output_sync_data.GetSpecifics().extension();
  const sync_pb::ExtensionSpecifics& input = entity.extension();

  // Check for field-by-field quality. It'd be nice if we could use
  // AssertionResults here (instead of EXPECT_EQ) so that we could get valid
  // line numbers, but it's not worth the ugliness of the verbose comparison.
  EXPECT_EQ(input.id(), output.id());
  EXPECT_EQ(input.name(), output.name());
  EXPECT_EQ(input.version(), output.version());
  EXPECT_EQ(input.update_url(), output.update_url());
  EXPECT_EQ(input.enabled(), output.enabled());
  EXPECT_EQ(input.incognito_enabled(), output.incognito_enabled());
  EXPECT_EQ(input.remote_install(), output.remote_install());
  EXPECT_EQ(input.installed_by_custodian(), output.installed_by_custodian());
  EXPECT_EQ(input.has_all_urls_enabled(), output.has_all_urls_enabled());
  if (input.has_all_urls_enabled())
    EXPECT_EQ(input.all_urls_enabled(), output.all_urls_enabled());
}

// Serializes an ExtensionSyncData into a protobuf structure and back again, and
// confirms that the input is the same as the output.
void SyncDataToProtobufEqual(const ExtensionSyncData& input) {
  syncer::SyncData sync_data = input.GetSyncData();
  scoped_ptr<ExtensionSyncData> output =
      ExtensionSyncData::CreateFromSyncData(sync_data);
  ASSERT_TRUE(output.get());

  EXPECT_EQ(input.id(), output->id());
  EXPECT_EQ(input.uninstalled(), output->uninstalled());
  EXPECT_EQ(input.enabled(), output->enabled());
  EXPECT_EQ(input.incognito_enabled(), output->incognito_enabled());
  EXPECT_EQ(input.remote_install(), output->remote_install());
  EXPECT_EQ(input.installed_by_custodian(), output->installed_by_custodian());
  EXPECT_EQ(input.all_urls_enabled(), output->all_urls_enabled());
  EXPECT_TRUE(input.version().Equals(output->version()));
  EXPECT_EQ(input.update_url(), output->update_url());
  EXPECT_EQ(input.name(), output->name());
}

}  // namespace

class ExtensionSyncDataTest : public testing::Test {
};

// Tests the conversion process from a protobuf to an ExtensionSyncData and vice
// versa.
TEST_F(ExtensionSyncDataTest, ExtensionSyncDataForExtension) {
  sync_pb::EntitySpecifics entity;
  sync_pb::ExtensionSpecifics* extension_specifics = entity.mutable_extension();
  extension_specifics->set_id(kValidId);
  extension_specifics->set_update_url(kValidUpdateUrl);
  extension_specifics->set_enabled(false);
  extension_specifics->set_incognito_enabled(true);
  extension_specifics->set_remote_install(false);
  extension_specifics->set_installed_by_custodian(false);
  extension_specifics->set_all_urls_enabled(true);
  extension_specifics->set_version(kVersion);
  extension_specifics->set_name(kName);

  // Check the serialize-deserialize process for proto to ExtensionSyncData.
  ProtobufToSyncDataEqual(entity);

  // Explicitly test that conversion to an ExtensionSyncData gets the correct
  // result (otherwise we just know that conversion to/from a proto gives us
  // the same result, but don't know that it's right).
  ExtensionSyncData extension_sync_data;
  extension_sync_data.PopulateFromExtensionSpecifics(*extension_specifics);
  EXPECT_EQ(kValidId, extension_sync_data.id());
  EXPECT_EQ(GURL(kValidUpdateUrl), extension_sync_data.update_url());
  EXPECT_FALSE(extension_sync_data.enabled());
  EXPECT_EQ(true, extension_sync_data.incognito_enabled());
  EXPECT_FALSE(extension_sync_data.remote_install());
  EXPECT_EQ(ExtensionSyncData::BOOLEAN_TRUE,
            extension_sync_data.all_urls_enabled());
  EXPECT_TRUE(Version(kVersion).Equals(extension_sync_data.version()));
  EXPECT_EQ(std::string(kName), extension_sync_data.name());

  // Check the serialize-deserialize process for ExtensionSyncData to proto.
  SyncDataToProtobufEqual(extension_sync_data);

  // The most important thing to test is the "all urls" bit, since it is a
  // tri-state boolean (and thus has more logic). Also flip another bit for a
  // sanity check.
  extension_specifics->set_all_urls_enabled(false);
  extension_specifics->set_incognito_enabled(false);
  ProtobufToSyncDataEqual(entity);

  extension_sync_data.PopulateFromExtensionSpecifics(*extension_specifics);
  EXPECT_EQ(ExtensionSyncData::BOOLEAN_FALSE,
            extension_sync_data.all_urls_enabled());
  EXPECT_FALSE(extension_sync_data.incognito_enabled());

  SyncDataToProtobufEqual(extension_sync_data);

  extension_specifics->clear_all_urls_enabled();
  ProtobufToSyncDataEqual(entity);

  extension_sync_data.PopulateFromExtensionSpecifics(*extension_specifics);
  EXPECT_FALSE(extension_specifics->has_all_urls_enabled());
  EXPECT_EQ(ExtensionSyncData::BOOLEAN_UNSET,
            extension_sync_data.all_urls_enabled());

  SyncDataToProtobufEqual(extension_sync_data);
}

class AppSyncDataTest : public testing::Test {
 public:
  AppSyncDataTest() {}
  ~AppSyncDataTest() override {}

  void SetRequiredExtensionValues(
      sync_pb::ExtensionSpecifics* extension_specifics) {
    extension_specifics->set_id(kValidId);
    extension_specifics->set_update_url(kValidUpdateUrl);
    extension_specifics->set_version(kVersion);
    extension_specifics->set_enabled(false);
    extension_specifics->set_disable_reasons(kValidDisableReasons);
    extension_specifics->set_incognito_enabled(true);
    extension_specifics->set_remote_install(false);
    extension_specifics->set_all_urls_enabled(true);
    extension_specifics->set_installed_by_custodian(false);
    extension_specifics->set_name(kName);
  }
};

TEST_F(AppSyncDataTest, SyncDataToExtensionSyncDataForApp) {
  sync_pb::EntitySpecifics entity;
  sync_pb::AppSpecifics* app_specifics = entity.mutable_app();
  app_specifics->set_app_launch_ordinal(
      syncer::StringOrdinal::CreateInitialOrdinal().ToInternalValue());
  app_specifics->set_page_ordinal(
      syncer::StringOrdinal::CreateInitialOrdinal().ToInternalValue());

  SetRequiredExtensionValues(app_specifics->mutable_extension());

  syncer::SyncData sync_data =
      syncer::SyncData::CreateLocalData("sync_tag", "non_unique_title", entity);

  scoped_ptr<ExtensionSyncData> app_sync_data =
      ExtensionSyncData::CreateFromSyncData(sync_data);
  ASSERT_TRUE(app_sync_data.get());
  EXPECT_EQ(app_specifics->app_launch_ordinal(),
            app_sync_data->app_launch_ordinal().ToInternalValue());
  EXPECT_EQ(app_specifics->page_ordinal(),
            app_sync_data->page_ordinal().ToInternalValue());
}

TEST_F(AppSyncDataTest, ExtensionSyncDataToSyncDataForApp) {
  sync_pb::EntitySpecifics entity;
  sync_pb::AppSpecifics* input_specifics = entity.mutable_app();
  input_specifics->set_app_launch_ordinal(
      syncer::StringOrdinal::CreateInitialOrdinal().ToInternalValue());
  input_specifics->set_page_ordinal(
      syncer::StringOrdinal::CreateInitialOrdinal().ToInternalValue());

  SetRequiredExtensionValues(input_specifics->mutable_extension());

  syncer::SyncData sync_data =
      syncer::SyncData::CreateLocalData("sync_tag", "non_unique_title", entity);
  scoped_ptr<ExtensionSyncData> app_sync_data =
      ExtensionSyncData::CreateFromSyncData(sync_data);
  ASSERT_TRUE(app_sync_data.get());

  syncer::SyncData output_sync_data = app_sync_data->GetSyncData();
  EXPECT_TRUE(sync_data.GetSpecifics().has_app());
  const sync_pb::AppSpecifics& output_specifics =
      output_sync_data.GetSpecifics().app();
  EXPECT_EQ(input_specifics->SerializeAsString(),
            output_specifics.SerializeAsString());
}

// Ensures that invalid StringOrdinals don't break ExtensionSyncData.
TEST_F(AppSyncDataTest, ExtensionSyncDataInvalidOrdinal) {
  sync_pb::EntitySpecifics entity;
  sync_pb::AppSpecifics* app_specifics = entity.mutable_app();
  // Set the ordinals as invalid.
  app_specifics->set_app_launch_ordinal("");
  app_specifics->set_page_ordinal("");

  SetRequiredExtensionValues(app_specifics->mutable_extension());

  syncer::SyncData sync_data =
      syncer::SyncData::CreateLocalData("sync_tag", "non_unique_title", entity);

  // There should be no issue loading the sync data.
  scoped_ptr<ExtensionSyncData> app_sync_data =
      ExtensionSyncData::CreateFromSyncData(sync_data);
  ASSERT_TRUE(app_sync_data.get());
  app_sync_data->GetSyncData();
}

}  // namespace extensions
