// 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 <stddef.h>

#include <memory>

#include "base/memory/weak_ptr.h"
#include "base/run_loop.h"
#include "chrome/browser/download/download_status_updater.h"
#include "components/download/public/common/mock_download_item.h"
#include "content/public/test/mock_download_manager.h"
#include "content/public/test/test_browser_thread_bundle.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"

using testing::AtLeast;
using testing::Invoke;
using testing::Mock;
using testing::Return;
using testing::SetArgPointee;
using testing::StrictMock;
using testing::WithArg;
using testing::_;

class TestDownloadStatusUpdater : public DownloadStatusUpdater {
 public:
  TestDownloadStatusUpdater()
      : notification_count_(0), acceptable_notification_item_(nullptr) {}
  void SetAcceptableNotificationItem(download::DownloadItem* item) {
    acceptable_notification_item_ = item;
  }
  size_t NotificationCount() {
    return notification_count_;
  }
 protected:
  void UpdateAppIconDownloadProgress(
      download::DownloadItem* download) override {
    ++notification_count_;
    if (acceptable_notification_item_)
      EXPECT_EQ(acceptable_notification_item_, download);
  }
 private:
  size_t notification_count_;
  download::DownloadItem* acceptable_notification_item_;
};

class DownloadStatusUpdaterTest : public testing::Test {
 public:
  DownloadStatusUpdaterTest() : updater_(new TestDownloadStatusUpdater()) {}

  ~DownloadStatusUpdaterTest() override {
    for (size_t mgr_idx = 0; mgr_idx < managers_.size(); ++mgr_idx) {
      EXPECT_CALL(*Manager(mgr_idx), RemoveObserver(_));
    }

    delete updater_;
    updater_ = nullptr;
    VerifyAndClearExpectations();

    managers_.clear();
    manager_items_.clear();
    all_owned_items_.clear();

    base::RunLoop().RunUntilIdle();  // Allow DownloadManager destruction.
  }

 protected:
  // Attach some number of DownloadManagers to the updater.
  void SetupManagers(int manager_count) {
    DCHECK_EQ(0U, managers_.size());
    for (int i = 0; i < manager_count; ++i) {
      managers_.push_back(
          std::make_unique<StrictMock<content::MockDownloadManager>>());
    }
  }

  void SetObserver(content::DownloadManager::Observer* observer) {
    manager_observers_[manager_observer_index_] = observer;
  }

  // Hook the specified manager into the updater.
  void LinkManager(int i) {
    content::MockDownloadManager* mgr = managers_[i].get();
    manager_observer_index_ = i;
    while (manager_observers_.size() <= static_cast<size_t>(i)) {
      manager_observers_.push_back(nullptr);
    }
    EXPECT_CALL(*mgr, IsManagerInitialized());
    EXPECT_CALL(*mgr, AddObserver(_))
        .WillOnce(WithArg<0>(Invoke(
            this, &DownloadStatusUpdaterTest::SetObserver)));
    updater_->AddManager(mgr);
  }

  // Add some number of Download items to a particular manager.
  void AddItems(int manager_index, int item_count, int in_progress_count) {
    DCHECK_GT(managers_.size(), static_cast<size_t>(manager_index));
    content::MockDownloadManager* manager = managers_[manager_index].get();

    if (manager_items_.size() <= static_cast<size_t>(manager_index))
      manager_items_.resize(manager_index+1);

    std::vector<download::DownloadItem*> item_list;
    for (int i = 0; i < item_count; ++i) {
      std::unique_ptr<download::MockDownloadItem> item =
          std::make_unique<StrictMock<download::MockDownloadItem>>();
      download::DownloadItem::DownloadState state =
          i < in_progress_count ? download::DownloadItem::IN_PROGRESS
                                : download::DownloadItem::CANCELLED;
      EXPECT_CALL(*item, GetState()).WillRepeatedly(Return(state));
      manager_items_[manager_index].push_back(item.get());
      all_owned_items_.push_back(std::move(item));
    }
    EXPECT_CALL(*manager, GetAllDownloads(_))
        .WillRepeatedly(SetArgPointee<0>(manager_items_[manager_index]));
  }

  // Return the specified manager.
  content::MockDownloadManager* Manager(int manager_index) {
    DCHECK_GT(managers_.size(), static_cast<size_t>(manager_index));
    return managers_[manager_index].get();
  }

  // Return the specified item.
  download::MockDownloadItem* Item(int manager_index, int item_index) {
    DCHECK_GT(manager_items_.size(), static_cast<size_t>(manager_index));
    DCHECK_GT(manager_items_[manager_index].size(),
              static_cast<size_t>(item_index));
    // All DownloadItems in manager_items_ are MockDownloadItems.
    return static_cast<download::MockDownloadItem*>(
        manager_items_[manager_index][item_index]);
  }

  // Set return values relevant to |DownloadStatusUpdater::GetProgress()|
  // for the specified item.
  void SetItemValues(int manager_index, int item_index,
                     int received_bytes, int total_bytes, bool notify) {
    download::MockDownloadItem* item(Item(manager_index, item_index));
    EXPECT_CALL(*item, GetReceivedBytes())
        .WillRepeatedly(Return(received_bytes));
    EXPECT_CALL(*item, GetTotalBytes())
        .WillRepeatedly(Return(total_bytes));
    if (notify)
      updater_->OnDownloadUpdated(managers_[manager_index].get(), item);
  }

  // Transition specified item to completed.
  void CompleteItem(int manager_index, int item_index) {
    download::MockDownloadItem* item(Item(manager_index, item_index));
    EXPECT_CALL(*item, GetState())
        .WillRepeatedly(Return(download::DownloadItem::COMPLETE));
    updater_->OnDownloadUpdated(managers_[manager_index].get(), item);
  }

  // Verify and clear all mocks expectations.
  void VerifyAndClearExpectations() {
    for (const auto& manager : managers_)
      Mock::VerifyAndClearExpectations(manager.get());
    for (auto it = manager_items_.begin(); it != manager_items_.end(); ++it)
      for (auto sit = it->begin(); sit != it->end(); ++sit)
        Mock::VerifyAndClearExpectations(*sit);
  }

  // The mocked download managers.
  std::vector<std::unique_ptr<content::MockDownloadManager>> managers_;
  // The download items being downloaded by those managers in |managers_|. The
  // top-level vector is the manager index, and the inner vector is the list of
  // items of that manager. The inner vector is a vector<DownloadItem*> for
  // compatibility with the return value of DownloadManager::GetAllDownloads().
  std::vector<std::vector<download::DownloadItem*>> manager_items_;
  // An owning container for items in |manager_items_|.
  std::vector<std::unique_ptr<download::DownloadItem>> all_owned_items_;
  int manager_observer_index_;

  std::vector<content::DownloadManager::Observer*> manager_observers_;

  // Pointer so we can verify that destruction triggers appropriate
  // changes.
  TestDownloadStatusUpdater* updater_;

  // Thread so that the DownloadManager (which is a DeleteOnUIThread
  // object) can be deleted.
  // TODO(rdsmith): This can be removed when the DownloadManager
  // is no longer required to be deleted on the UI thread.
  content::TestBrowserThreadBundle test_browser_thread_bundle_;
};

// Test null updater.
TEST_F(DownloadStatusUpdaterTest, Basic) {
  float progress = -1;
  int download_count = -1;
  EXPECT_TRUE(updater_->GetProgress(&progress, &download_count));
  EXPECT_FLOAT_EQ(0.0f, progress);
  EXPECT_EQ(0, download_count);
}

// Test updater with null manager.
TEST_F(DownloadStatusUpdaterTest, OneManagerNoItems) {
  SetupManagers(1);
  AddItems(0, 0, 0);
  LinkManager(0);
  VerifyAndClearExpectations();

  float progress = -1;
  int download_count = -1;
  EXPECT_CALL(*managers_[0], GetAllDownloads(_))
      .WillRepeatedly(SetArgPointee<0>(manager_items_[0]));
  EXPECT_TRUE(updater_->GetProgress(&progress, &download_count));
  EXPECT_FLOAT_EQ(0.0f, progress);
  EXPECT_EQ(0, download_count);
}

// Test updater with non-null manager, including transition an item to
// |download::DownloadItem::COMPLETE| and adding a new item.
TEST_F(DownloadStatusUpdaterTest, OneManagerManyItems) {
  SetupManagers(1);
  AddItems(0, 3, 2);
  LinkManager(0);

  // Prime items
  SetItemValues(0, 0, 10, 20, false);
  SetItemValues(0, 1, 50, 60, false);
  SetItemValues(0, 2, 90, 90, false);

  float progress = -1;
  int download_count = -1;
  EXPECT_TRUE(updater_->GetProgress(&progress, &download_count));
  EXPECT_FLOAT_EQ((10+50)/(20.0f+60), progress);
  EXPECT_EQ(2, download_count);

  // Transition one item to completed and confirm progress is updated
  // properly.
  CompleteItem(0, 0);
  EXPECT_TRUE(updater_->GetProgress(&progress, &download_count));
  EXPECT_FLOAT_EQ(50/60.0f, progress);
  EXPECT_EQ(1, download_count);

  // Add a new item to manager and confirm progress is updated properly.
  AddItems(0, 1, 1);
  SetItemValues(0, 3, 150, 200, false);
  manager_observers_[0]->OnDownloadCreated(
      managers_[0].get(), manager_items_[0][manager_items_[0].size() - 1]);

  EXPECT_TRUE(updater_->GetProgress(&progress, &download_count));
  EXPECT_FLOAT_EQ((50+150)/(60+200.0f), progress);
  EXPECT_EQ(2, download_count);
}

// Test to ensure that the download progress notification is called correctly.
TEST_F(DownloadStatusUpdaterTest, ProgressNotification) {
  size_t expected_notifications = updater_->NotificationCount();
  SetupManagers(1);
  AddItems(0, 2, 2);
  LinkManager(0);

  // Expect two notifications, one for each item; which item will come first
  // isn't defined so it cannot be tested.
  expected_notifications += 2;
  ASSERT_EQ(expected_notifications, updater_->NotificationCount());

  // Make progress on the first item.
  updater_->SetAcceptableNotificationItem(Item(0, 0));
  SetItemValues(0, 0, 10, 20, true);
  ++expected_notifications;
  ASSERT_EQ(expected_notifications, updater_->NotificationCount());

  // Second item completes!
  updater_->SetAcceptableNotificationItem(Item(0, 1));
  CompleteItem(0, 1);
  ++expected_notifications;
  ASSERT_EQ(expected_notifications, updater_->NotificationCount());

  // First item completes.
  updater_->SetAcceptableNotificationItem(Item(0, 0));
  CompleteItem(0, 0);
  ++expected_notifications;
  ASSERT_EQ(expected_notifications, updater_->NotificationCount());

  updater_->SetAcceptableNotificationItem(nullptr);
}

// Confirm we recognize the situation where we have an unknown size.
TEST_F(DownloadStatusUpdaterTest, UnknownSize) {
  SetupManagers(1);
  AddItems(0, 2, 2);
  LinkManager(0);

  // Prime items
  SetItemValues(0, 0, 10, 20, false);
  SetItemValues(0, 1, 50, -1, false);

  float progress = -1;
  int download_count = -1;
  EXPECT_FALSE(updater_->GetProgress(&progress, &download_count));
}

// Test many null managers.
TEST_F(DownloadStatusUpdaterTest, ManyManagersNoItems) {
  SetupManagers(1);
  AddItems(0, 0, 0);
  LinkManager(0);

  float progress = -1;
  int download_count = -1;
  EXPECT_TRUE(updater_->GetProgress(&progress, &download_count));
  EXPECT_FLOAT_EQ(0.0f, progress);
  EXPECT_EQ(0, download_count);
}

// Test many managers with all items complete.
TEST_F(DownloadStatusUpdaterTest, ManyManagersEmptyItems) {
  SetupManagers(2);
  AddItems(0, 3, 0);
  LinkManager(0);
  AddItems(1, 3, 0);
  LinkManager(1);

  float progress = -1;
  int download_count = -1;
  EXPECT_TRUE(updater_->GetProgress(&progress, &download_count));
  EXPECT_FLOAT_EQ(0.0f, progress);
  EXPECT_EQ(0, download_count);
}

// Test many managers with some non-complete items.
TEST_F(DownloadStatusUpdaterTest, ManyManagersMixedItems) {
  SetupManagers(2);
  AddItems(0, 3, 2);
  LinkManager(0);
  AddItems(1, 3, 1);
  LinkManager(1);

  SetItemValues(0, 0, 10, 20, false);
  SetItemValues(0, 1, 50, 60, false);
  SetItemValues(1, 0, 80, 90, false);

  float progress = -1;
  int download_count = -1;
  EXPECT_TRUE(updater_->GetProgress(&progress, &download_count));
  EXPECT_FLOAT_EQ((10+50+80)/(20.0f+60+90), progress);
  EXPECT_EQ(3, download_count);
}
