// 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 "chrome/browser/predictors/loading_data_collector.h"

#include <iostream>
#include <memory>
#include <utility>
#include <vector>

#include "base/test/metrics/histogram_tester.h"
#include "chrome/browser/history/history_service_factory.h"
#include "chrome/browser/predictors/loading_predictor_config.h"
#include "chrome/browser/predictors/loading_test_util.h"
#include "chrome/test/base/testing_profile.h"
#include "content/public/test/test_browser_thread_bundle.h"
#include "content/public/test/test_utils.h"
#include "net/http/http_response_headers.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"

using testing::StrictMock;

namespace predictors {

class LoadingDataCollectorTest : public testing::Test {
 public:
  LoadingDataCollectorTest() : profile_(std::make_unique<TestingProfile>()) {
    LoadingPredictorConfig config;
    PopulateTestConfig(&config);
    mock_predictor_ =
        std::make_unique<StrictMock<MockResourcePrefetchPredictor>>(
            config, profile_.get()),
    collector_ = std::make_unique<LoadingDataCollector>(mock_predictor_.get(),
                                                        nullptr, config);
  }

  void SetUp() override {
    LoadingDataCollector::SetAllowPortInUrlsForTesting(false);
    content::RunAllTasksUntilIdle();  // Runs the DB lookup.
  }

 protected:
  content::TestBrowserThreadBundle thread_bundle_;
  std::unique_ptr<TestingProfile> profile_;

  std::unique_ptr<StrictMock<MockResourcePrefetchPredictor>> mock_predictor_;
  std::unique_ptr<LoadingDataCollector> collector_;
};

TEST_F(LoadingDataCollectorTest, HandledResourceTypes) {
  EXPECT_TRUE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_STYLESHEET, "bogus/mime-type"));
  EXPECT_TRUE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_STYLESHEET, ""));
  EXPECT_FALSE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_WORKER, "text/css"));
  EXPECT_FALSE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_WORKER, ""));
  EXPECT_TRUE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_PREFETCH, "text/css"));
  EXPECT_FALSE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_PREFETCH, "bogus/mime-type"));
  EXPECT_FALSE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_PREFETCH, ""));
  EXPECT_TRUE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_PREFETCH, "application/font-woff"));
  EXPECT_TRUE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_PREFETCH, "font/woff2"));
  EXPECT_FALSE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_XHR, ""));
  EXPECT_FALSE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_XHR, "bogus/mime-type"));
  EXPECT_TRUE(LoadingDataCollector::IsHandledResourceType(
      content::RESOURCE_TYPE_XHR, "application/javascript"));
}

TEST_F(LoadingDataCollectorTest, ShouldRecordMainFrameLoad) {
  auto http_request = CreateResourceLoadInfo("http://www.google.com");
  EXPECT_TRUE(LoadingDataCollector::ShouldRecordResourceLoad(*http_request));

  auto https_request = CreateResourceLoadInfo("https://www.google.com");
  EXPECT_TRUE(LoadingDataCollector::ShouldRecordResourceLoad(*https_request));

  auto file_request = CreateResourceLoadInfo("file://www.google.com");
  EXPECT_FALSE(LoadingDataCollector::ShouldRecordResourceLoad(*file_request));

  auto https_request_with_port =
      CreateResourceLoadInfo("https://www.google.com:666");
  EXPECT_FALSE(
      LoadingDataCollector::ShouldRecordResourceLoad(*https_request_with_port));
}

TEST_F(LoadingDataCollectorTest, ShouldRecordSubresourceLoad) {
  // Protocol.
  auto http_image_request = CreateResourceLoadInfo(
      "http://www.google.com/cat.png", content::RESOURCE_TYPE_IMAGE);
  EXPECT_TRUE(
      LoadingDataCollector::ShouldRecordResourceLoad(*http_image_request));

  auto https_image_request = CreateResourceLoadInfo(
      "https://www.google.com/cat.png", content::RESOURCE_TYPE_IMAGE);
  EXPECT_TRUE(
      LoadingDataCollector::ShouldRecordResourceLoad(*https_image_request));

  auto https_image_request_with_port = CreateResourceLoadInfo(
      "https://www.google.com:666/cat.png", content::RESOURCE_TYPE_IMAGE);
  EXPECT_FALSE(LoadingDataCollector::ShouldRecordResourceLoad(
      *https_image_request_with_port));

  auto file_image_request = CreateResourceLoadInfo(
      "file://www.google.com/cat.png", content::RESOURCE_TYPE_IMAGE);
  EXPECT_FALSE(
      LoadingDataCollector::ShouldRecordResourceLoad(*file_image_request));

  // ResourceType.
  auto sub_frame_request = CreateResourceLoadInfo(
      "http://www.google.com/frame.html", content::RESOURCE_TYPE_SUB_FRAME);
  EXPECT_FALSE(
      LoadingDataCollector::ShouldRecordResourceLoad(*sub_frame_request));

  auto font_request =
      CreateResourceLoadInfo("http://www.google.com/comic-sans-ms.woff",
                             content::RESOURCE_TYPE_FONT_RESOURCE);
  EXPECT_TRUE(LoadingDataCollector::ShouldRecordResourceLoad(*font_request));

  // From MIME Type.
  auto prefetch_image_request = CreateResourceLoadInfo(
      "http://www.google.com/cat.png", content::RESOURCE_TYPE_PREFETCH);
  prefetch_image_request->mime_type = "image/png";
  EXPECT_TRUE(
      LoadingDataCollector::ShouldRecordResourceLoad(*prefetch_image_request));

  auto prefetch_unknown_image_request = CreateResourceLoadInfo(
      "http://www.google.com/cat.png", content::RESOURCE_TYPE_PREFETCH);
  prefetch_unknown_image_request->mime_type = "image/my-wonderful-format";
  EXPECT_FALSE(LoadingDataCollector::ShouldRecordResourceLoad(
      *prefetch_unknown_image_request));

  auto prefetch_font_request =
      CreateResourceLoadInfo("http://www.google.com/comic-sans-ms.woff",
                             content::RESOURCE_TYPE_PREFETCH);
  prefetch_font_request->mime_type = "font/woff";
  EXPECT_TRUE(
      LoadingDataCollector::ShouldRecordResourceLoad(*prefetch_font_request));

  auto prefetch_unknown_font_request =
      CreateResourceLoadInfo("http://www.google.com/comic-sans-ms.woff",
                             content::RESOURCE_TYPE_PREFETCH);
  prefetch_unknown_font_request->mime_type = "font/woff-woff";
  EXPECT_FALSE(LoadingDataCollector::ShouldRecordResourceLoad(
      *prefetch_unknown_font_request));
}

// Single navigation that will be recorded. Will check for duplicate
// resources and also for number of resources saved.
TEST_F(LoadingDataCollectorTest, SimpleNavigation) {
  const SessionID kTabId = SessionID::FromSerializedValue(1);
  auto navigation_id = CreateNavigationID(kTabId, "http://www.google.com");
  collector_->RecordStartNavigation(navigation_id);
  collector_->RecordFinishNavigation(navigation_id, navigation_id,
                                     /* is_error_page */ false);
  EXPECT_EQ(1U, collector_->inflight_navigations_.size());

  std::vector<content::mojom::ResourceLoadInfoPtr> resources;
  resources.push_back(CreateResourceLoadInfo("http://www.google.com"));
  collector_->RecordResourceLoadComplete(navigation_id, *resources.back());
  resources.push_back(CreateResourceLoadInfo(
      "http://google.com/style1.css", content::RESOURCE_TYPE_STYLESHEET));
  collector_->RecordResourceLoadComplete(navigation_id, *resources.back());
  resources.push_back(CreateResourceLoadInfo("http://google.com/script1.js",
                                             content::RESOURCE_TYPE_SCRIPT));
  collector_->RecordResourceLoadComplete(navigation_id, *resources.back());
  resources.push_back(CreateResourceLoadInfo("http://google.com/script2.js",
                                             content::RESOURCE_TYPE_SCRIPT));
  collector_->RecordResourceLoadComplete(navigation_id, *resources.back());
  resources.push_back(CreateResourceLoadInfo("http://google.com/script1.js",
                                             content::RESOURCE_TYPE_SCRIPT));
  collector_->RecordResourceLoadComplete(navigation_id, *resources.back());
  resources.push_back(CreateResourceLoadInfo("http://google.com/image1.png",
                                             content::RESOURCE_TYPE_IMAGE));
  collector_->RecordResourceLoadComplete(navigation_id, *resources.back());
  resources.push_back(CreateResourceLoadInfo("http://google.com/image2.png",
                                             content::RESOURCE_TYPE_IMAGE));
  collector_->RecordResourceLoadComplete(navigation_id, *resources.back());
  resources.push_back(CreateResourceLoadInfo(
      "http://google.com/style2.css", content::RESOURCE_TYPE_STYLESHEET));
  collector_->RecordResourceLoadComplete(navigation_id, *resources.back());
  resources.push_back(
      CreateResourceLoadInfo("http://static.google.com/style2-no-store.css",
                             content::RESOURCE_TYPE_STYLESHEET,
                             /* always_access_network */ true));
  collector_->RecordResourceLoadComplete(navigation_id, *resources.back());
  resources.push_back(CreateResourceLoadInfoWithRedirects(
      {"http://reader.google.com/style.css",
       "http://dev.null.google.com/style.css"},
      content::RESOURCE_TYPE_STYLESHEET));
  collector_->RecordResourceLoadComplete(navigation_id, *resources.back());

  auto summary = CreatePageRequestSummary("http://www.google.com",
                                          "http://www.google.com", resources);

  EXPECT_CALL(*mock_predictor_,
              RecordPageRequestSummaryProxy(testing::Pointee(summary)));

  collector_->RecordMainFrameLoadComplete(navigation_id);
}

TEST_F(LoadingDataCollectorTest, SimpleRedirect) {
  const SessionID kTabId = SessionID::FromSerializedValue(1);
  auto navigation_id = CreateNavigationID(kTabId, "http://fb.com/google");
  collector_->RecordStartNavigation(navigation_id);
  EXPECT_EQ(1U, collector_->inflight_navigations_.size());

  auto main_frame = CreateResourceLoadInfoWithRedirects(
      {"http://fb.com/google", "http://facebook.com/google",
       "https://facebook.com/google"});

  auto new_navigation_id =
      CreateNavigationID(kTabId, "https://facebook.com/google");
  collector_->RecordFinishNavigation(navigation_id, new_navigation_id,
                                     /* is_error_page */ false);
  EXPECT_EQ(1U, collector_->inflight_navigations_.size());
  EXPECT_EQ(navigation_id.main_frame_url,
            collector_->inflight_navigations_[new_navigation_id]->initial_url);
  collector_->RecordResourceLoadComplete(new_navigation_id, *main_frame);

  std::vector<content::mojom::ResourceLoadInfoPtr> resources;
  resources.push_back(std::move(main_frame));
  EXPECT_CALL(
      *mock_predictor_,
      RecordPageRequestSummaryProxy(testing::Pointee(CreatePageRequestSummary(
          "https://facebook.com/google", "http://fb.com/google", resources))));

  collector_->RecordMainFrameLoadComplete(new_navigation_id);
}

// Tests that RecordNavigationFinish without the corresponding
// RecordNavigationStart works fine.
TEST_F(LoadingDataCollectorTest, RecordStartNavigationMissing) {
  const SessionID kTabId = SessionID::FromSerializedValue(1);
  auto navigation_id = CreateNavigationID(kTabId, "http://bbc.com");
  auto new_navigation_id = CreateNavigationID(kTabId, "https://www.bbc.com");

  // collector_->RecordStartNavigtion(navigation_id) is missing.
  collector_->RecordFinishNavigation(navigation_id, new_navigation_id,
                                     /* is_error_page */ false);
  EXPECT_EQ(1U, collector_->inflight_navigations_.size());
  EXPECT_EQ(navigation_id.main_frame_url,
            collector_->inflight_navigations_[new_navigation_id]->initial_url);
}

TEST_F(LoadingDataCollectorTest, RecordFailedNavigation) {
  const SessionID kTabId = SessionID::FromSerializedValue(1);
  auto navigation_id = CreateNavigationID(kTabId, "http://bbc.com");

  collector_->RecordStartNavigation(navigation_id);
  EXPECT_EQ(1U, collector_->inflight_navigations_.size());
  collector_->RecordFinishNavigation(navigation_id, navigation_id,
                                     /* is_error_page */ true);
  EXPECT_TRUE(collector_->inflight_navigations_.empty());
}

TEST_F(LoadingDataCollectorTest, ManyNavigations) {
  const SessionID kTabId1 = SessionID::FromSerializedValue(1);
  const SessionID kTabId2 = SessionID::FromSerializedValue(2);
  const SessionID kTabId3 = SessionID::FromSerializedValue(3);
  const SessionID kTabId4 = SessionID::FromSerializedValue(4);

  auto navigation_id1 = CreateNavigationID(kTabId1, "http://www.google.com");
  auto navigation_id2 = CreateNavigationID(kTabId2, "http://www.google.com");
  auto navigation_id3 = CreateNavigationID(kTabId3, "http://www.yahoo.com");

  collector_->RecordStartNavigation(navigation_id1);
  EXPECT_EQ(1U, collector_->inflight_navigations_.size());
  collector_->RecordStartNavigation(navigation_id2);
  EXPECT_EQ(2U, collector_->inflight_navigations_.size());
  collector_->RecordStartNavigation(navigation_id3);
  EXPECT_EQ(3U, collector_->inflight_navigations_.size());

  // Insert another with same navigation id. It should replace.
  auto navigation_id4 = CreateNavigationID(kTabId1, "http://www.nike.com");
  collector_->RecordStartNavigation(navigation_id4);
  EXPECT_EQ(3U, collector_->inflight_navigations_.size());

  auto navigation_id5 = CreateNavigationID(kTabId2, "http://www.google.com");
  // Change this creation time so that it will go away on the next insert.
  navigation_id5.creation_time =
      base::TimeTicks::Now() - base::TimeDelta::FromDays(1);
  collector_->RecordStartNavigation(navigation_id5);
  EXPECT_EQ(3U, collector_->inflight_navigations_.size());

  auto navigation_id6 = CreateNavigationID(kTabId4, "http://www.shoes.com");
  collector_->RecordStartNavigation(navigation_id6);
  EXPECT_EQ(3U, collector_->inflight_navigations_.size());

  EXPECT_TRUE(collector_->inflight_navigations_.find(navigation_id3) !=
              collector_->inflight_navigations_.end());
  EXPECT_TRUE(collector_->inflight_navigations_.find(navigation_id4) !=
              collector_->inflight_navigations_.end());
  EXPECT_TRUE(collector_->inflight_navigations_.find(navigation_id6) !=
              collector_->inflight_navigations_.end());
}

TEST_F(LoadingDataCollectorTest, RecordResourceLoadComplete) {
  const SessionID kTabId = SessionID::FromSerializedValue(1);
  // If there is no inflight navigation, nothing happens.
  auto navigation_id = CreateNavigationID(kTabId, "http://www.google.com");
  auto resource1 = CreateResourceLoadInfo("http://google.com/style1.css",
                                          content::RESOURCE_TYPE_STYLESHEET);
  collector_->RecordResourceLoadComplete(navigation_id, *resource1);
  EXPECT_TRUE(collector_->inflight_navigations_.empty());

  // Add an inflight navigation.
  collector_->RecordStartNavigation(navigation_id);
  EXPECT_EQ(1U, collector_->inflight_navigations_.size());

  // Now add a few subresources.
  auto resource2 = CreateResourceLoadInfo("http://google.com/script1.js",
                                          content::RESOURCE_TYPE_SCRIPT);
  auto resource3 = CreateResourceLoadInfo("http://google.com/script2.js",
                                          content::RESOURCE_TYPE_SCRIPT);
  collector_->RecordResourceLoadComplete(navigation_id, *resource1);
  collector_->RecordResourceLoadComplete(navigation_id, *resource2);
  collector_->RecordResourceLoadComplete(navigation_id, *resource3);

  EXPECT_EQ(1U, collector_->inflight_navigations_.size());
}

}  // namespace predictors
