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

#include "components/component_updater/component_updater_service.h"

#include <algorithm>
#include <cstdint>
#include <memory>
#include <optional>
#include <string>
#include <utility>
#include <vector>

#include "base/containers/to_vector.h"
#include "base/files/file_path.h"
#include "base/functional/bind.h"
#include "base/functional/callback_helpers.h"
#include "base/memory/raw_ptr.h"
#include "base/memory/ref_counted.h"
#include "base/run_loop.h"
#include "base/task/sequenced_task_runner.h"
#include "base/test/metrics/histogram_tester.h"
#include "base/test/task_environment.h"
#include "base/values.h"
#include "build/branding_buildflags.h"
#include "components/component_updater/component_updater_service_internal.h"
#include "components/prefs/testing_pref_service.h"
#include "components/update_client/crx_update_item.h"
#include "components/update_client/test_configurator.h"
#include "components/update_client/test_installer.h"
#include "components/update_client/update_client.h"
#include "components/update_client/update_client_errors.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"

namespace component_updater {

using Configurator = ::update_client::Configurator;
using Result = ::update_client::CrxInstaller::Result;
using TestConfigurator = ::update_client::TestConfigurator;
using UpdateClient = ::update_client::UpdateClient;

using ::testing::_;
using ::testing::AnyNumber;
using ::testing::Invoke;
using ::testing::Mock;
using ::testing::Return;
using ::testing::Unused;

class MockInstaller : public update_client::CrxInstaller {
 public:
  MockInstaller() = default;
  MOCK_METHOD5(Install,
               void(const base::FilePath& unpack_path,
                    const std::string& public_key,
                    std::unique_ptr<InstallParams> install_params,
                    ProgressCallback progress_callback,
                    Callback callback));
  MOCK_METHOD1(GetInstalledFile,
               std::optional<base::FilePath>(const std::string& file));
  MOCK_METHOD0(Uninstall, bool());

 private:
  ~MockInstaller() override = default;
};

class MockUpdateClient : public UpdateClient {
 public:
  MockUpdateClient() = default;

  MOCK_METHOD1(AddObserver, void(Observer* observer));
  MOCK_METHOD1(RemoveObserver, void(Observer* observer));
  MOCK_METHOD4(
      Install,
      base::RepeatingClosure(const std::string& id,
                             CrxDataCallback crx_data_callback,
                             CrxStateChangeCallback crx_state_change_callback,
                             Callback callback));
  MOCK_METHOD5(Update,
               void(const std::vector<std::string>& ids,
                    CrxDataCallback crx_data_callback,
                    CrxStateChangeCallback crx_state_change_callback,
                    bool is_foreground,
                    Callback callback));
  MOCK_METHOD5(CheckForUpdate,
               void(const std::string& ids,
                    CrxDataCallback crx_data_callback,
                    CrxStateChangeCallback crx_state_change_callback,
                    bool is_foreground,
                    Callback callback));
  MOCK_CONST_METHOD2(GetCrxUpdateState,
                     bool(const std::string& id, CrxUpdateItem* update_item));
  MOCK_CONST_METHOD1(IsUpdating, bool(const std::string& id));
  MOCK_METHOD0(Stop, void());
  MOCK_METHOD3(SendPing,
               void(const CrxComponent& crx_component,
                    PingParams ping_params,
                    Callback callback));
  MOCK_METHOD2(SendRegistrationPing,
               void(const CrxComponent& crx_component, Callback callback));

 private:
  ~MockUpdateClient() override = default;
};

class MockServiceObserver : public ServiceObserver {
 public:
  MOCK_METHOD1(OnEvent, void(const update_client::CrxUpdateItem&));
};

class MockUpdateScheduler : public UpdateScheduler {
 public:
  MOCK_METHOD4(Schedule,
               void(base::TimeDelta initial_delay,
                    base::TimeDelta delay,
                    const UserTask& user_task,
                    const OnStopTaskCallback& on_stop));
  MOCK_METHOD0(Stop, void());
};

class LoopHandler {
 public:
  explicit LoopHandler(int max_cnt, base::OnceClosure quit_closure)
      : max_cnt_(max_cnt), quit_closure_(std::move(quit_closure)) {}

  base::RepeatingClosure OnInstall(const std::string&,
                                   UpdateClient::CrxDataCallback,
                                   UpdateClient::CrxStateChangeCallback,
                                   Callback callback) {
    Handle(std::move(callback));
    return base::DoNothing();
  }

  void OnUpdate(const std::vector<std::string>&,
                UpdateClient::CrxDataCallback,
                UpdateClient::CrxStateChangeCallback,
                bool is_foreground,
                Callback callback) {
    EXPECT_FALSE(is_foreground);
    Handle(std::move(callback));
  }

 private:
  void Handle(Callback callback) {
    ++cnt_;
    if (cnt_ >= max_cnt_) {
      base::SequencedTaskRunner::GetCurrentDefault()->PostTask(
          FROM_HERE, std::move(quit_closure_));
    }
    std::move(callback).Run(update_client::Error::NONE);
  }

  const int max_cnt_ = 0;
  base::OnceClosure quit_closure_;
  int cnt_ = 0;
};

class ComponentUpdaterTest : public testing::Test {
 public:
  ComponentUpdaterTest();
  ComponentUpdaterTest(const ComponentUpdaterTest&) = delete;
  ComponentUpdaterTest& operator=(const ComponentUpdaterTest&) = delete;
  ~ComponentUpdaterTest() override;

  // Makes the full path to a component updater test file.
  const base::FilePath test_file(const char* file);

  MockUpdateClient& update_client() { return *update_client_; }
  ComponentUpdateService& component_updater() { return *component_updater_; }
  scoped_refptr<TestConfigurator> configurator() const { return config_; }
  base::OnceClosure quit_closure() { return runloop_.QuitClosure(); }
  MockUpdateScheduler& scheduler() { return *scheduler_; }

 protected:
  void RunThreads();

 private:
  void RunUpdateTask(const UpdateScheduler::UserTask& user_task);
  void Schedule(base::TimeDelta initial_delay,
                base::TimeDelta delay,
                const UpdateScheduler::UserTask& user_task,
                const UpdateScheduler::OnStopTaskCallback& on_stop);

  base::test::TaskEnvironment task_environment_;
  base::RunLoop runloop_;

  std::unique_ptr<TestingPrefServiceSimple> pref_ =
      std::make_unique<TestingPrefServiceSimple>();
  scoped_refptr<TestConfigurator> config_;
  scoped_refptr<MockUpdateClient> update_client_ =
      base::MakeRefCounted<MockUpdateClient>();
  std::unique_ptr<ComponentUpdateService> component_updater_;
  raw_ptr<MockUpdateScheduler> scheduler_;
};

class OnDemandTester {
 public:
  void OnDemand(ComponentUpdateService* cus,
                const std::string& id,
                OnDemandUpdater::Priority priority);
  update_client::Error error() const { return error_; }

 private:
  void OnDemandComplete(update_client::Error error);

  update_client::Error error_ = update_client::Error::NONE;
};

void OnDemandTester::OnDemand(ComponentUpdateService* cus,
                              const std::string& id,
                              OnDemandUpdater::Priority priority) {
  cus->GetOnDemandUpdater().OnDemandUpdate(
      id, priority,
      base::BindOnce(&OnDemandTester::OnDemandComplete,
                     base::Unretained(this)));
}

void OnDemandTester::OnDemandComplete(update_client::Error error) {
  error_ = error;
}

std::unique_ptr<ComponentUpdateService> TestComponentUpdateServiceFactory(
    scoped_refptr<Configurator> config) {
  EXPECT_TRUE(config);
  return std::make_unique<CrxUpdateService>(
      config, std::make_unique<MockUpdateScheduler>(),
      base::MakeRefCounted<MockUpdateClient>(), "");
}

ComponentUpdaterTest::ComponentUpdaterTest() {
  EXPECT_CALL(update_client(), AddObserver(_));
  auto scheduler = std::make_unique<MockUpdateScheduler>();
  scheduler_ = scheduler.get();
  ON_CALL(*scheduler_, Schedule(_, _, _, _))
      .WillByDefault(Invoke(this, &ComponentUpdaterTest::Schedule));
  RegisterComponentUpdateServicePrefs(pref_->registry());
  update_client::RegisterPrefs(pref_->registry());
  config_ = base::MakeRefCounted<TestConfigurator>(pref_.get());
  component_updater_ = std::make_unique<CrxUpdateService>(
      config_, std::move(scheduler), update_client_, "");
}

ComponentUpdaterTest::~ComponentUpdaterTest() {
  EXPECT_CALL(update_client(), RemoveObserver(_));
}

void ComponentUpdaterTest::RunThreads() {
  runloop_.Run();
}

void ComponentUpdaterTest::RunUpdateTask(
    const UpdateScheduler::UserTask& user_task) {
  task_environment_.GetMainThreadTaskRunner()->PostTask(
      FROM_HERE, base::BindRepeating(
                     [](const UpdateScheduler::UserTask& user_task,
                        ComponentUpdaterTest* test) {
                       user_task.Run(base::BindOnce(
                           [](const UpdateScheduler::UserTask& user_task,
                              ComponentUpdaterTest* test) {
                             test->RunUpdateTask(user_task);
                           },
                           user_task, base::Unretained(test)));
                     },
                     user_task, base::Unretained(this)));
}

void ComponentUpdaterTest::Schedule(
    base::TimeDelta initial_delay,
    base::TimeDelta delay,
    const UpdateScheduler::UserTask& user_task,
    const UpdateScheduler::OnStopTaskCallback& on_stop) {
  RunUpdateTask(user_task);
}

TEST_F(ComponentUpdaterTest, AddObserver) {
  MockServiceObserver observer;
  EXPECT_CALL(update_client(), AddObserver(&observer));
  EXPECT_CALL(update_client(), Stop());
  EXPECT_CALL(scheduler(), Stop());
  component_updater().AddObserver(&observer);
}

TEST_F(ComponentUpdaterTest, RemoveObserver) {
  MockServiceObserver observer;
  EXPECT_CALL(update_client(), RemoveObserver(&observer));
  EXPECT_CALL(update_client(), Stop());
  EXPECT_CALL(scheduler(), Stop());
  component_updater().RemoveObserver(&observer);
}

// Tests that UpdateClient::Update is called by the timer loop when
// components are registered, and the component update starts.
// Also tests that Uninstall is called when a component is unregistered.
TEST_F(ComponentUpdaterTest, RegisterComponent) {
  base::HistogramTester ht;

  scoped_refptr<MockInstaller> installer =
      base::MakeRefCounted<MockInstaller>();
  EXPECT_CALL(*installer, Uninstall()).WillOnce(Return(true));

  const std::string id1 = "abagagagagagagagagagagagagagagag";
  const std::string id2 = "jebgalgnebhfojomionfpkfelancnnkf";

  ComponentRegistration component1(
      id1, /*name=*/{}, base::ToVector(update_client::abag_hash),
      base::Version("1.0"),
      /*fingerprint=*/{}, {},
      /*action_handler=*/nullptr, installer,
      /*requires_network_encryption=*/false,
      /*supports_group_policy_enable_component_updates=*/true,
      /*allow_cached_copies=*/true,
      /*allow_updates_on_metered_connection=*/true,
      /*allow_updates=*/true);

  ComponentRegistration component2(
      id2, /*name=*/{}, base::ToVector(update_client::jebg_hash),
      base::Version("0.9"),
      /*fingerprint=*/{}, /*installer_attributes=*/{},
      /*action_handler=*/nullptr, installer,
      /*requires_network_encryption=*/false,
      /*supports_group_policy_enable_component_updates=*/true,
      /*allow_cached_copies=*/true,
      /*allow_updates_on_metered_connection=*/true,
      /*allow_updates=*/true);

  // Quit after two update checks have fired.
  LoopHandler loop_handler(2, quit_closure());
  EXPECT_CALL(update_client(), Update(_, _, _, _, _))
      .WillRepeatedly(Invoke(&loop_handler, &LoopHandler::OnUpdate));

  EXPECT_CALL(update_client(), IsUpdating(id1));
  EXPECT_CALL(update_client(), Stop());
  EXPECT_CALL(scheduler(), Schedule(_, _, _, _));
  EXPECT_CALL(scheduler(), Stop());

  EXPECT_TRUE(component_updater().RegisterComponent(component1));
  EXPECT_TRUE(component_updater().RegisterComponent(component2));

  RunThreads();
  EXPECT_TRUE(component_updater().UnregisterComponent(id1));

  ht.ExpectUniqueSample("ComponentUpdater.Calls", 1, 2);
  ht.ExpectUniqueSample("ComponentUpdater.UpdateCompleteResult", 0, 2);
  ht.ExpectTotalCount("ComponentUpdater.UpdateCompleteTime", 2);
}

// Tests that on-demand updates invoke UpdateClient::Install.
TEST_F(ComponentUpdaterTest, OnDemandUpdate) {
  base::HistogramTester ht;

  // Don't run periodic update task.
  ON_CALL(scheduler(), Schedule(_, _, _, _)).WillByDefault(Return());

  auto& cus = component_updater();

  // Tests calling OnDemand for an unregistered component. This call results in
  // an error, which is recorded by the OnDemandTester instance. Since the
  // component was not registered, the call is ignored for UMA metrics.
  OnDemandTester ondemand_tester_component_not_registered;
  ondemand_tester_component_not_registered.OnDemand(
      &cus, "ihfokbkgjpifnbbojhneepfflplebdkc",
      OnDemandUpdater::Priority::FOREGROUND);

  // Register two components, then call |OnDemand| for each component, with
  // foreground and background priorities. Expect calls to |Schedule| because
  // components have registered, calls to |Install| and |Update| corresponding
  // to each |OnDemand| invocation, and calls to |Stop| when the mocks are
  // torn down.
  LoopHandler loop_handler(2, quit_closure());
  EXPECT_CALL(scheduler(), Schedule(_, _, _, _));
  EXPECT_CALL(update_client(), Install(_, _, _, _))
      .WillOnce(Invoke(&loop_handler, &LoopHandler::OnInstall));
  EXPECT_CALL(update_client(), Update(_, _, _, _, _))
      .WillOnce(Invoke(&loop_handler, &LoopHandler::OnUpdate));
  EXPECT_CALL(update_client(), Stop());
  EXPECT_CALL(scheduler(), Stop());

  {
    EXPECT_TRUE(cus.RegisterComponent(ComponentRegistration(
        "jebgalgnebhfojomionfpkfelancnnkf", /*name=*/{},
        base::ToVector(update_client::jebg_hash), base::Version("0.9"),
        /*fingerprint=*/{}, /*installer_attributes=*/{},
        /*action_handler=*/nullptr, base::MakeRefCounted<MockInstaller>(),
        /*requires_network_encryption=*/false,
        /*supports_group_policy_enable_component_updates=*/true,
        /*allow_cached_copies=*/true,
        /*allow_updates_on_metered_connection=*/true,
        /*allow_updates=*/true)));
  }
  {
    EXPECT_TRUE(cus.RegisterComponent(ComponentRegistration(
        "abagagagagagagagagagagagagagagag", /*name=*/{},
        base::ToVector(update_client::abag_hash), base::Version("0.9"),
        /*fingerprint=*/{}, /*installer_attributes=*/{},
        /*action_handler=*/nullptr, base::MakeRefCounted<MockInstaller>(),
        /*requires_network_encryption=*/false,
        /*supports_group_policy_enable_component_updates=*/true,
        /*allow_cached_copies=*/true,
        /*allow_updates_on_metered_connection=*/true,
        /*allow_updates=*/true)));
  }

  OnDemandTester ondemand_tester;
  ondemand_tester.OnDemand(&cus, "jebgalgnebhfojomionfpkfelancnnkf",
                           OnDemandUpdater::Priority::FOREGROUND);
  ondemand_tester.OnDemand(&cus, "abagagagagagagagagagagagagagagag",
                           OnDemandUpdater::Priority::BACKGROUND);
  RunThreads();

  EXPECT_EQ(update_client::Error::INVALID_ARGUMENT,
            ondemand_tester_component_not_registered.error());
  EXPECT_EQ(update_client::Error::NONE, ondemand_tester.error());

  ht.ExpectUniqueSample("ComponentUpdater.Calls", 0, 2);
  ht.ExpectUniqueSample("ComponentUpdater.UpdateCompleteResult", 0, 2);
  ht.ExpectTotalCount("ComponentUpdater.UpdateCompleteTime", 2);
}

// Tests that throttling an update invokes UpdateClient::Install.
TEST_F(ComponentUpdaterTest, MaybeThrottle) {
  base::HistogramTester ht;

  // Don't run periodic update task.
  ON_CALL(scheduler(), Schedule(_, _, _, _)).WillByDefault(Return());

  LoopHandler loop_handler(1, quit_closure());
  EXPECT_CALL(update_client(), Install(_, _, _, _))
      .WillOnce(Invoke(&loop_handler, &LoopHandler::OnInstall));
  EXPECT_CALL(update_client(), Stop());
  EXPECT_CALL(scheduler(), Schedule(_, _, _, _));
  EXPECT_CALL(scheduler(), Stop());

  EXPECT_TRUE(component_updater().RegisterComponent(ComponentRegistration(
      "jebgalgnebhfojomionfpkfelancnnkf", /*name=*/{},
      base::ToVector(update_client::jebg_hash), base::Version("0.9"), {},
      /*installer_attributes=*/{}, /*action_handler=*/nullptr,
      base::MakeRefCounted<MockInstaller>(),
      /*requires_network_encryption=*/false,
      /*supports_group_policy_enable_component_updates=*/true,
      /*allow_cached_copies=*/true,
      /*allow_updates_on_metered_connection=*/true,
      /*allow_updates=*/true)));
  component_updater().MaybeThrottle("jebgalgnebhfojomionfpkfelancnnkf",
                                    base::DoNothing());

  RunThreads();

  ht.ExpectUniqueSample("ComponentUpdater.Calls", 0, 1);
  ht.ExpectUniqueSample("ComponentUpdater.UpdateCompleteResult", 0, 1);
  ht.ExpectTotalCount("ComponentUpdater.UpdateCompleteTime", 1);
}

TEST_F(ComponentUpdaterTest, ComponentDetails) {
  const std::string id = "abagagagagagagagagagagagagagagag";
  const std::string name = "test_name";

  const auto version = base::Version("1.0");

  ComponentRegistration component(
      id, name, base::ToVector(update_client::abag_hash), version,
      /*fingerprint=*/{}, {},
      /*action_handler=*/nullptr, base::MakeRefCounted<MockInstaller>(),
      /*requires_network_encryption=*/false,
      /*supports_group_policy_enable_component_updates=*/true,
      /*allow_cached_copies=*/true,
      /*allow_updates_on_metered_connection=*/true,
      /*allow_updates=*/true);

  ASSERT_TRUE(component_updater().RegisterComponent(component));

  CrxUpdateItem item;
  ASSERT_TRUE(component_updater().GetComponentDetails(id, &item));
  ASSERT_TRUE(item.component);
  const CrxComponent& registered = *item.component;

  EXPECT_EQ(registered.app_id, id);
  EXPECT_EQ(registered.version, version);
  EXPECT_EQ(registered.name, name);

#if BUILDFLAG(CHROME_FOR_TESTING)
  // In Chrome for Testing component updates are disabled.
  EXPECT_FALSE(registered.updates_enabled);
#else
  EXPECT_TRUE(registered.updates_enabled);
#endif  // BUILDFLAG(CHROME_FOR_TESTING)
}

TEST_F(ComponentUpdaterTest, UpdatesDisabled) {
  const std::string id = "abagagagagagagagagagagagagagagag";
  const std::string name = "test_name";

  const auto version = base::Version("1.0");

  ComponentRegistration component(
      id, name, base::ToVector(update_client::abag_hash), version,
      /*fingerprint=*/{}, {},
      /*action_handler=*/nullptr, base::MakeRefCounted<MockInstaller>(),
      /*requires_network_encryption=*/false,
      /*supports_group_policy_enable_component_updates=*/true,
      /*allow_cached_copies=*/true,
      /*allow_updates_on_metered_connection=*/true,
      /*allow_updates=*/false);

  ASSERT_TRUE(component_updater().RegisterComponent(component));

  CrxUpdateItem item;
  ASSERT_TRUE(component_updater().GetComponentDetails(id, &item));
  ASSERT_TRUE(item.component);
  const CrxComponent& registered = *item.component;

  EXPECT_FALSE(registered.updates_enabled);
}

}  // namespace component_updater
