// Copyright 2013 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/update_client/ping_manager.h"

#include <stdint.h>

#include <limits>
#include <memory>
#include <string>
#include <utility>
#include <vector>

#include "base/bind.h"
#include "base/json/json_reader.h"
#include "base/memory/ref_counted.h"
#include "base/run_loop.h"
#include "base/test/scoped_task_environment.h"
#include "base/threading/thread_task_runner_handle.h"
#include "base/version.h"
#include "components/update_client/component.h"
#include "components/update_client/protocol_definition.h"
#include "components/update_client/protocol_serializer.h"
#include "components/update_client/test_configurator.h"
#include "components/update_client/update_engine.h"
#include "components/update_client/url_loader_post_interceptor.h"
#include "net/url_request/url_request_test_util.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "third_party/re2/src/re2/re2.h"

using std::string;

namespace update_client {

class PingManagerTest : public testing::Test,
                        public testing::WithParamInterface<bool> {
 public:
  PingManagerTest();
  ~PingManagerTest() override {}

  PingManager::Callback MakePingCallback();
  scoped_refptr<UpdateContext> MakeMockUpdateContext() const;

  // Overrides from testing::Test.
  void SetUp() override;
  void TearDown() override;

  void PingSentCallback(int error, const std::string& response);

 protected:
  void Quit();
  void RunThreads();

  scoped_refptr<TestConfigurator> config_;
  scoped_refptr<PingManager> ping_manager_;

  bool use_JSON_ = false;

  int error_ = -1;
  std::string response_;

 private:
  base::test::ScopedTaskEnvironment scoped_task_environment_;
  base::OnceClosure quit_closure_;
};

PingManagerTest::PingManagerTest()
    : scoped_task_environment_(
          base::test::ScopedTaskEnvironment::MainThreadType::IO) {
  config_ = base::MakeRefCounted<TestConfigurator>();
}

void PingManagerTest::SetUp() {
  use_JSON_ = GetParam();
  config_->SetUseJSON(use_JSON_);
  ping_manager_ = base::MakeRefCounted<PingManager>(config_);
}

void PingManagerTest::TearDown() {
  // Run the threads until they are idle to allow the clean up
  // of the network interceptors on the IO thread.
  scoped_task_environment_.RunUntilIdle();
  ping_manager_ = nullptr;
}

void PingManagerTest::RunThreads() {
  base::RunLoop runloop;
  quit_closure_ = runloop.QuitClosure();
  runloop.Run();
}

void PingManagerTest::Quit() {
  if (!quit_closure_.is_null())
    std::move(quit_closure_).Run();
}

PingManager::Callback PingManagerTest::MakePingCallback() {
  return base::BindOnce(&PingManagerTest::PingSentCallback,
                        base::Unretained(this));
}

void PingManagerTest::PingSentCallback(int error, const std::string& response) {
  error_ = error;
  response_ = response;
  Quit();
}

scoped_refptr<UpdateContext> PingManagerTest::MakeMockUpdateContext() const {
  return base::MakeRefCounted<UpdateContext>(
      config_, false, std::vector<std::string>(),
      UpdateClient::CrxDataCallback(), UpdateEngine::NotifyObserversCallback(),
      UpdateEngine::Callback(), nullptr);
}

// This test is parameterized for using JSON or XML serialization. |true| means
// JSON serialization is used.
INSTANTIATE_TEST_CASE_P(Parameterized, PingManagerTest, testing::Bool());

TEST_P(PingManagerTest, SendPing) {
  auto interceptor = std::make_unique<URLLoaderPostInterceptor>(
      config_->test_url_loader_factory());
  EXPECT_TRUE(interceptor);

  const auto update_context = MakeMockUpdateContext();
  {
    // Test eventresult="1" is sent for successful updates.
    Component component(*update_context, "abc");
    component.crx_component_ = CrxComponent();
    component.crx_component_->version = base::Version("1.0");
    component.state_ = std::make_unique<Component::StateUpdated>(&component);
    component.previous_version_ = base::Version("1.0");
    component.next_version_ = base::Version("2.0");
    component.AppendEvent(component.MakeEventUpdateComplete());

    EXPECT_TRUE(interceptor->ExpectRequest(std::make_unique<AnyMatch>()));
    ping_manager_->SendPing(component, MakePingCallback());
    RunThreads();

    EXPECT_EQ(1, interceptor->GetCount()) << interceptor->GetRequestsAsString();
    const auto msg = interceptor->GetRequestBody(0);
    if (use_JSON_) {
      const auto root = base::JSONReader().Read(msg);
      const auto* request = root->FindKey("request");
      ASSERT_TRUE(request);
      EXPECT_TRUE(request->FindKey("@os"));
      EXPECT_EQ("fake_prodid", request->FindKey("@updater")->GetString());
      EXPECT_EQ("crx2,crx3", request->FindKey("acceptformat")->GetString());
      EXPECT_TRUE(request->FindKey("arch"));
      EXPECT_EQ("cr", request->FindKey("dedup")->GetString());
      EXPECT_LT(0, request->FindPath({"hw", "physmemory"})->GetInt());
      EXPECT_EQ("fake_lang", request->FindKey("lang")->GetString());
      EXPECT_TRUE(request->FindKey("nacl_arch"));
      EXPECT_EQ("fake_channel_string",
                request->FindKey("prodchannel")->GetString());
      EXPECT_EQ("30.0", request->FindKey("prodversion")->GetString());
      EXPECT_EQ("3.1", request->FindKey("protocol")->GetString());
      EXPECT_TRUE(request->FindKey("requestid"));
      EXPECT_TRUE(request->FindKey("sessionid"));
      EXPECT_EQ("fake_channel_string",
                request->FindKey("updaterchannel")->GetString());
      EXPECT_EQ("30.0", request->FindKey("updaterversion")->GetString());

      EXPECT_TRUE(request->FindPath({"os", "arch"})->is_string());
      EXPECT_EQ("Fake Operating System",
                request->FindPath({"os", "platform"})->GetString());
      EXPECT_TRUE(request->FindPath({"os", "version"})->is_string());

      const auto& app = request->FindKey("app")->GetList()[0];
      EXPECT_EQ("abc", app.FindKey("appid")->GetString());
      EXPECT_EQ("1.0", app.FindKey("version")->GetString());
      const auto& event = app.FindKey("event")->GetList()[0];
      EXPECT_EQ(1, event.FindKey("eventresult")->GetInt());
      EXPECT_EQ(3, event.FindKey("eventtype")->GetInt());
      EXPECT_EQ("2.0", event.FindKey("nextversion")->GetString());
      EXPECT_EQ("1.0", event.FindKey("previousversion")->GetString());
    } else {
      constexpr char regex[] =
          R"(<\?xml version="1\.0" encoding="UTF-8"\?>)"
          R"(<request protocol="3\.1" )"
          R"(dedup="cr" acceptformat="crx2,crx3" extra="foo" )"
          R"(sessionid="{[-\w]{36}}" requestid="{[-\w]{36}}" )"
          R"(updater="fake_prodid" updaterversion="30\.0" prodversion="30\.0" )"
          R"(lang="fake_lang" os="\w+" arch="\w+" nacl_arch="[-\w]+" )"
          R"((wow64="1" )?)"
          R"(updaterchannel="fake_channel_string" )"
          R"(prodchannel="fake_channel_string">)"
          R"(<hw physmemory="[0-9]+"/>)"
          R"(<os platform="Fake Operating System" arch="[,-.\w]+" )"
          R"(version="[-.\w]+"( sp="[\s\w]+")?/>)"
          R"(<app appid="abc" version="1\.0">)"
          R"(<event eventresult="1" eventtype="3" )"
          R"(nextversion="2\.0" previousversion="1\.0"/></app></request>)";
      EXPECT_TRUE(RE2::FullMatch(msg, regex)) << msg;
    }

    // Check the ping request does not carry the specific extra request headers.
    const auto headers = std::get<1>(interceptor->GetRequests()[0]);
    EXPECT_FALSE(headers.HasHeader("X-Goog-Update-Interactivity"));
    EXPECT_FALSE(headers.HasHeader("X-Goog-Update-Updater"));
    EXPECT_FALSE(headers.HasHeader("X-Goog-Update-AppId"));
    interceptor->Reset();
  }

  {
    // Test eventresult="0" is sent for failed updates.
    Component component(*update_context, "abc");
    component.crx_component_ = CrxComponent();
    component.crx_component_->version = base::Version("1.0");
    component.state_ =
        std::make_unique<Component::StateUpdateError>(&component);
    component.previous_version_ = base::Version("1.0");
    component.next_version_ = base::Version("2.0");
    component.AppendEvent(component.MakeEventUpdateComplete());

    EXPECT_TRUE(interceptor->ExpectRequest(std::make_unique<AnyMatch>()));
    ping_manager_->SendPing(component, MakePingCallback());
    RunThreads();

    EXPECT_EQ(1, interceptor->GetCount()) << interceptor->GetRequestsAsString();
    const auto msg = interceptor->GetRequestBody(0);
    if (use_JSON_) {
      const auto root = base::JSONReader().Read(msg);
      const auto* request = root->FindKey("request");
      const auto& app = request->FindKey("app")->GetList()[0];
      EXPECT_EQ("abc", app.FindKey("appid")->GetString());
      EXPECT_EQ("1.0", app.FindKey("version")->GetString());
      const auto& event = app.FindKey("event")->GetList()[0];
      EXPECT_EQ(0, event.FindKey("eventresult")->GetInt());
      EXPECT_EQ(3, event.FindKey("eventtype")->GetInt());
      EXPECT_EQ("2.0", event.FindKey("nextversion")->GetString());
      EXPECT_EQ("1.0", event.FindKey("previousversion")->GetString());
    } else {
      constexpr char regex[] =
          R"(<app appid="abc" version="1\.0">)"
          R"(<event eventresult="0" eventtype="3" )"
          R"(nextversion="2\.0" previousversion="1\.0"/></app>)";
      EXPECT_TRUE(RE2::PartialMatch(msg, regex)) << msg;
    }
    interceptor->Reset();
  }

  {
    // Test the error values and the fingerprints.
    Component component(*update_context, "abc");
    component.crx_component_ = CrxComponent();
    component.crx_component_->version = base::Version("1.0");
    component.state_ =
        std::make_unique<Component::StateUpdateError>(&component);
    component.previous_version_ = base::Version("1.0");
    component.next_version_ = base::Version("2.0");
    component.previous_fp_ = "prev fp";
    component.next_fp_ = "next fp";
    component.error_category_ = ErrorCategory::kDownload;
    component.error_code_ = 2;
    component.extra_code1_ = -1;
    component.diff_error_category_ = ErrorCategory::kService;
    component.diff_error_code_ = 20;
    component.diff_extra_code1_ = -10;
    component.crx_diffurls_.push_back(GURL("http://host/path"));
    component.AppendEvent(component.MakeEventUpdateComplete());

    EXPECT_TRUE(interceptor->ExpectRequest(std::make_unique<AnyMatch>()));
    ping_manager_->SendPing(component, MakePingCallback());
    RunThreads();

    EXPECT_EQ(1, interceptor->GetCount()) << interceptor->GetRequestsAsString();
    const auto msg = interceptor->GetRequestBody(0);
    if (use_JSON_) {
      const auto root = base::JSONReader().Read(msg);
      const auto* request = root->FindKey("request");
      const auto& app = request->FindKey("app")->GetList()[0];
      EXPECT_EQ("abc", app.FindKey("appid")->GetString());
      EXPECT_EQ("1.0", app.FindKey("version")->GetString());
      const auto& event = app.FindKey("event")->GetList()[0];
      EXPECT_EQ(0, event.FindKey("eventresult")->GetInt());
      EXPECT_EQ(3, event.FindKey("eventtype")->GetInt());
      EXPECT_EQ("2.0", event.FindKey("nextversion")->GetString());
      EXPECT_EQ("1.0", event.FindKey("previousversion")->GetString());
      EXPECT_EQ(4, event.FindKey("differrorcat")->GetInt());
      EXPECT_EQ(20, event.FindKey("differrorcode")->GetInt());
      EXPECT_EQ(-10, event.FindKey("diffextracode1")->GetInt());
      EXPECT_EQ(0, event.FindKey("diffresult")->GetInt());
      EXPECT_EQ(1, event.FindKey("errorcat")->GetInt());
      EXPECT_EQ(2, event.FindKey("errorcode")->GetInt());
      EXPECT_EQ(-1, event.FindKey("extracode1")->GetInt());
      EXPECT_EQ("next fp", event.FindKey("nextfp")->GetString());
      EXPECT_EQ("prev fp", event.FindKey("previousfp")->GetString());
    } else {
      constexpr char regex[] =
          R"(<app appid="abc" version="1\.0">)"
          R"(<event differrorcat="4" differrorcode="20" )"
          R"(diffextracode1="-10" diffresult="0" errorcat="1" errorcode="2" )"
          R"(eventresult="0" eventtype="3" extracode1="-1" nextfp="next fp" )"
          R"(nextversion="2\.0" previousfp="prev fp" previousversion="1\.0"/>)"
          R"(</app>)";
      EXPECT_TRUE(RE2::PartialMatch(msg, regex)) << msg;
    }
    interceptor->Reset();
  }

  {
    // Test an invalid |next_version| is not serialized.
    Component component(*update_context, "abc");
    component.crx_component_ = CrxComponent();
    component.crx_component_->version = base::Version("1.0");
    component.state_ =
        std::make_unique<Component::StateUpdateError>(&component);
    component.previous_version_ = base::Version("1.0");

    component.AppendEvent(component.MakeEventUpdateComplete());

    EXPECT_TRUE(interceptor->ExpectRequest(std::make_unique<AnyMatch>()));
    ping_manager_->SendPing(component, MakePingCallback());
    RunThreads();

    EXPECT_EQ(1, interceptor->GetCount()) << interceptor->GetRequestsAsString();
    const auto msg = interceptor->GetRequestBody(0);
    if (use_JSON_) {
      const auto root = base::JSONReader().Read(msg);
      const auto* request = root->FindKey("request");
      const auto& app = request->FindKey("app")->GetList()[0];
      EXPECT_EQ("abc", app.FindKey("appid")->GetString());
      EXPECT_EQ("1.0", app.FindKey("version")->GetString());
      const auto& event = app.FindKey("event")->GetList()[0];
      EXPECT_EQ(0, event.FindKey("eventresult")->GetInt());
      EXPECT_EQ(3, event.FindKey("eventtype")->GetInt());
      EXPECT_EQ("1.0", event.FindKey("previousversion")->GetString());
    } else {
      constexpr char regex[] =
          R"(<app appid="abc" version="1\.0">)"
          R"(<event eventresult="0" eventtype="3" previousversion="1\.0"/>)"
          R"(</app>)";
      EXPECT_TRUE(RE2::PartialMatch(msg, regex)) << msg;
    }
    interceptor->Reset();
  }

  {
    // Test a valid |previouversion| and |next_version| = base::Version("0")
    // are serialized correctly under <event...> for uninstall.
    Component component(*update_context, "abc");
    component.crx_component_ = CrxComponent();
    component.Uninstall(base::Version("1.2.3.4"), 0);
    component.AppendEvent(component.MakeEventUninstalled());

    EXPECT_TRUE(interceptor->ExpectRequest(std::make_unique<AnyMatch>()));
    ping_manager_->SendPing(component, MakePingCallback());
    RunThreads();

    EXPECT_EQ(1, interceptor->GetCount()) << interceptor->GetRequestsAsString();
    const auto msg = interceptor->GetRequestBody(0);
    if (use_JSON_) {
      const auto root = base::JSONReader().Read(msg);
      const auto* request = root->FindKey("request");
      const auto& app = request->FindKey("app")->GetList()[0];
      EXPECT_EQ("abc", app.FindKey("appid")->GetString());
      EXPECT_EQ("1.2.3.4", app.FindKey("version")->GetString());
      const auto& event = app.FindKey("event")->GetList()[0];
      EXPECT_EQ(1, event.FindKey("eventresult")->GetInt());
      EXPECT_EQ(4, event.FindKey("eventtype")->GetInt());
      EXPECT_EQ("1.2.3.4", event.FindKey("previousversion")->GetString());
      EXPECT_EQ("0", event.FindKey("nextversion")->GetString());
    } else {
      constexpr char regex[] =
          R"(<app appid="abc" version="1\.2\.3\.4">)"
          R"(<event eventresult="1" eventtype="4" )"
          R"(nextversion="0" previousversion="1\.2\.3\.4"/></app>)";
      EXPECT_TRUE(RE2::PartialMatch(msg, regex)) << msg;
    }
    interceptor->Reset();
  }

  {
    // Test the download metrics.
    Component component(*update_context, "abc");
    component.crx_component_ = CrxComponent();
    component.crx_component_->version = base::Version("1.0");
    component.state_ = std::make_unique<Component::StateUpdated>(&component);
    component.previous_version_ = base::Version("1.0");
    component.next_version_ = base::Version("2.0");
    component.AppendEvent(component.MakeEventUpdateComplete());

    CrxDownloader::DownloadMetrics download_metrics;
    download_metrics.url = GURL("http://host1/path1");
    download_metrics.downloader = CrxDownloader::DownloadMetrics::kUrlFetcher;
    download_metrics.error = -1;
    download_metrics.downloaded_bytes = 123;
    download_metrics.total_bytes = 456;
    download_metrics.download_time_ms = 987;
    component.AppendEvent(component.MakeEventDownloadMetrics(download_metrics));

    download_metrics = CrxDownloader::DownloadMetrics();
    download_metrics.url = GURL("http://host2/path2");
    download_metrics.downloader = CrxDownloader::DownloadMetrics::kBits;
    download_metrics.error = 0;
    download_metrics.downloaded_bytes = 1230;
    download_metrics.total_bytes = 4560;
    download_metrics.download_time_ms = 9870;
    component.AppendEvent(component.MakeEventDownloadMetrics(download_metrics));

    download_metrics = CrxDownloader::DownloadMetrics();
    download_metrics.url = GURL("http://host3/path3");
    download_metrics.downloader = CrxDownloader::DownloadMetrics::kBits;
    download_metrics.error = 0;
    download_metrics.downloaded_bytes = kProtocolMaxInt;
    download_metrics.total_bytes = kProtocolMaxInt - 1;
    download_metrics.download_time_ms = kProtocolMaxInt - 2;
    component.AppendEvent(component.MakeEventDownloadMetrics(download_metrics));

    EXPECT_TRUE(interceptor->ExpectRequest(std::make_unique<AnyMatch>()));
    ping_manager_->SendPing(component, MakePingCallback());
    RunThreads();

    EXPECT_EQ(1, interceptor->GetCount()) << interceptor->GetRequestsAsString();
    const auto msg = interceptor->GetRequestBody(0);
    if (use_JSON_) {
      const auto root = base::JSONReader().Read(msg);
      const auto* request = root->FindKey("request");
      const auto& app = request->FindKey("app")->GetList()[0];
      EXPECT_EQ("abc", app.FindKey("appid")->GetString());
      EXPECT_EQ("1.0", app.FindKey("version")->GetString());
      EXPECT_EQ(4u, app.FindKey("event")->GetList().size());
      {
        const auto& event = app.FindKey("event")->GetList()[0];
        EXPECT_EQ(1, event.FindKey("eventresult")->GetInt());
        EXPECT_EQ(3, event.FindKey("eventtype")->GetInt());
        EXPECT_EQ("2.0", event.FindKey("nextversion")->GetString());
        EXPECT_EQ("1.0", event.FindKey("previousversion")->GetString());
      }
      {
        const auto& event = app.FindKey("event")->GetList()[1];
        EXPECT_EQ(0, event.FindKey("eventresult")->GetInt());
        EXPECT_EQ(14, event.FindKey("eventtype")->GetInt());
        EXPECT_EQ(987, event.FindKey("download_time_ms")->GetDouble());
        EXPECT_EQ(123, event.FindKey("downloaded")->GetDouble());
        EXPECT_EQ("direct", event.FindKey("downloader")->GetString());
        EXPECT_EQ(-1, event.FindKey("errorcode")->GetInt());
        EXPECT_EQ("2.0", event.FindKey("nextversion")->GetString());
        EXPECT_EQ("1.0", event.FindKey("previousversion")->GetString());
        EXPECT_EQ(456, event.FindKey("total")->GetDouble());
        EXPECT_EQ("http://host1/path1", event.FindKey("url")->GetString());
      }
      {
        const auto& event = app.FindKey("event")->GetList()[2];
        EXPECT_EQ(1, event.FindKey("eventresult")->GetInt());
        EXPECT_EQ(14, event.FindKey("eventtype")->GetInt());
        EXPECT_EQ(9870, event.FindKey("download_time_ms")->GetDouble());
        EXPECT_EQ(1230, event.FindKey("downloaded")->GetDouble());
        EXPECT_EQ("bits", event.FindKey("downloader")->GetString());
        EXPECT_EQ("2.0", event.FindKey("nextversion")->GetString());
        EXPECT_EQ("1.0", event.FindKey("previousversion")->GetString());
        EXPECT_EQ(4560, event.FindKey("total")->GetDouble());
        EXPECT_EQ("http://host2/path2", event.FindKey("url")->GetString());
      }
      {
        const auto& event = app.FindKey("event")->GetList()[3];
        EXPECT_EQ(1, event.FindKey("eventresult")->GetInt());
        EXPECT_EQ(14, event.FindKey("eventtype")->GetInt());
        EXPECT_EQ(9007199254740990,
                  event.FindKey("download_time_ms")->GetDouble());
        EXPECT_EQ(9007199254740992, event.FindKey("downloaded")->GetDouble());
        EXPECT_EQ("bits", event.FindKey("downloader")->GetString());
        EXPECT_EQ("2.0", event.FindKey("nextversion")->GetString());
        EXPECT_EQ("1.0", event.FindKey("previousversion")->GetString());
        EXPECT_EQ(9007199254740991, event.FindKey("total")->GetDouble());
        EXPECT_EQ("http://host3/path3", event.FindKey("url")->GetString());
      }
    } else {
      constexpr char regex[] =
          R"(<app appid="abc" version="1\.0">)"
          R"(<event eventresult="1" eventtype="3" )"
          R"(nextversion="2\.0" previousversion="1\.0"/>)"
          R"(<event download_time_ms="987" )"
          R"(downloaded="123" downloader="direct" )"
          R"(errorcode="-1" eventresult="0" eventtype="14" )"
          R"(nextversion="2\.0" previousversion="1\.0" total="456" )"
          R"(url="http://host1/path1"/>)"
          R"(<event download_time_ms="9870" downloaded="1230" )"
          R"(downloader="bits" )"
          R"(eventresult="1" eventtype="14" nextversion="2\.0" )"
          R"(previousversion="1\.0" total="4560" url="http://host2/path2"/>)"
          R"(<event download_time_ms="9007199254740990" )"
          R"(downloaded="9007199254740992" downloader="bits" )"
          R"(eventresult="1" eventtype="14" nextversion="2.0" )"
          R"(previousversion="1.0" total="9007199254740991" )"
          R"(url="http://host3/path3"/></app>)";
      EXPECT_TRUE(RE2::PartialMatch(msg, regex)) << msg;
    }
    interceptor->Reset();
  }
}

// Tests that sending the ping fails when the component requires encryption but
// the ping URL is unsecure.
TEST_P(PingManagerTest, RequiresEncryption) {
  config_->SetPingUrl(GURL("http:\\foo\bar"));

  const auto update_context = MakeMockUpdateContext();

  Component component(*update_context, "abc");
  component.crx_component_ = CrxComponent();
  component.crx_component_->version = base::Version("1.0");

  // The default value for |requires_network_encryption| is true.
  EXPECT_TRUE(component.crx_component_->requires_network_encryption);

  component.state_ = std::make_unique<Component::StateUpdated>(&component);
  component.previous_version_ = base::Version("1.0");
  component.next_version_ = base::Version("2.0");
  component.AppendEvent(component.MakeEventUpdateComplete());

  ping_manager_->SendPing(component, MakePingCallback());
  RunThreads();

  EXPECT_EQ(-2, error_);
}

}  // namespace update_client
