// Copyright 2017 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 <memory>

#include "base/bind.h"
#include "base/bind_helpers.h"
#include "base/files/file_path.h"
#include "base/logging.h"
#include "base/memory/ptr_util.h"
#include "base/test/scoped_task_environment.h"
#include "components/leveldb_proto/testing/fake_db.h"
#include "media/base/test_data_util.h"
#include "media/base/video_codecs.h"
#include "media/capabilities/video_decode_stats.pb.h"
#include "media/capabilities/video_decode_stats_db_impl.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "ui/gfx/geometry/size.h"

using leveldb_proto::test::FakeDB;
using testing::Pointee;
using testing::Eq;

namespace media {

class VideoDecodeStatsDBImplTest : public ::testing::Test {
 public:
  VideoDecodeStatsDBImplTest() = default;

  void SetUp() override {
    // Fake DB simply wraps a std::map with the LevelDB interface. We own the
    // map and will delete it in TearDown().
    fake_db_map_ = std::make_unique<FakeDB<DecodeStatsProto>::EntryMap>();
    // |stats_db_| will own this pointer, but we hold a reference to control
    // its behavior.
    fake_db_ = new FakeDB<DecodeStatsProto>(fake_db_map_.get());

    // Make our DB wrapper and kick off Initialize. Each test should start
    // by completing initialize, calling fake_db_->InitCallback(...) and
    // verifying the callback argument.
    stats_db_ = std::make_unique<VideoDecodeStatsDBImpl>(
        std::unique_ptr<FakeDB<DecodeStatsProto>>(fake_db_),
        base::FilePath(FILE_PATH_LITERAL("/fake/path")));
    stats_db_->Initialize(base::BindOnce(
        &VideoDecodeStatsDBImplTest::OnInitialize, base::Unretained(this)));
  }

  void TearDown() override {
    stats_db_.reset();
    fake_db_map_.reset();
  }

  // Unwraps move-only parameters to pass to the mock function.
  void GetDecodeStatsCb(
      bool success,
      std::unique_ptr<VideoDecodeStatsDB::DecodeStatsEntry> entry) {
    MockGetDecodeStatsCb(success, entry.get());
  }

  MOCK_METHOD1(OnInitialize, void(bool success));

  MOCK_METHOD2(MockGetDecodeStatsCb,
               void(bool success, VideoDecodeStatsDB::DecodeStatsEntry* entry));

  MOCK_METHOD1(MockAppendDecodeStatsCb, void(bool success));

  MOCK_METHOD0(MockDestroyStatsCb, void());

 protected:
  using VideoDescKey = VideoDecodeStatsDB::VideoDescKey;
  using DecodeStatsEntry = VideoDecodeStatsDB::DecodeStatsEntry;

  base::test::ScopedTaskEnvironment scoped_task_environment_;

  // See documentation in SetUp()
  std::unique_ptr<FakeDB<DecodeStatsProto>::EntryMap> fake_db_map_;
  FakeDB<DecodeStatsProto>* fake_db_;
  std::unique_ptr<VideoDecodeStatsDBImpl> stats_db_;

 private:
  DISALLOW_COPY_AND_ASSIGN(VideoDecodeStatsDBImplTest);
};

TEST_F(VideoDecodeStatsDBImplTest, ReadExpectingNothing) {
  EXPECT_CALL(*this, OnInitialize(true));
  fake_db_->InitCallback(true);

  VideoDescKey key = VideoDescKey::MakeBucketedKey(VP9PROFILE_PROFILE3,
                                                   gfx::Size(1024, 768), 60);

  // Database is empty. Expect null entry.
  EXPECT_CALL(*this, MockGetDecodeStatsCb(true, nullptr));
  stats_db_->GetDecodeStats(
      key, base::BindOnce(&VideoDecodeStatsDBImplTest::GetDecodeStatsCb,
                          base::Unretained(this)));

  fake_db_->GetCallback(true);
}

TEST_F(VideoDecodeStatsDBImplTest, WriteReadAndDestroy) {
  EXPECT_CALL(*this, OnInitialize(true));
  fake_db_->InitCallback(true);

  VideoDescKey key = VideoDescKey::MakeBucketedKey(VP9PROFILE_PROFILE3,
                                                   gfx::Size(1024, 768), 60);
  VideoDecodeStatsDB::DecodeStatsEntry entry(1000, 2, 10);

  EXPECT_CALL(*this, MockAppendDecodeStatsCb(true));
  stats_db_->AppendDecodeStats(
      key, entry,
      base::BindOnce(&VideoDecodeStatsDBImplTest::MockAppendDecodeStatsCb,
                     base::Unretained(this)));
  fake_db_->GetCallback(true);
  fake_db_->UpdateCallback(true);

  EXPECT_CALL(*this, MockGetDecodeStatsCb(true, Pointee(Eq(entry))));
  stats_db_->GetDecodeStats(
      key, base::BindOnce(&VideoDecodeStatsDBImplTest::GetDecodeStatsCb,
                          base::Unretained(this)));
  fake_db_->GetCallback(true);

  // Append the same entry again.
  EXPECT_CALL(*this, MockAppendDecodeStatsCb(true));
  stats_db_->AppendDecodeStats(
      key, entry,
      base::BindOnce(&VideoDecodeStatsDBImplTest::MockAppendDecodeStatsCb,
                     base::Unretained(this)));
  fake_db_->GetCallback(true);
  fake_db_->UpdateCallback(true);

  // Expect to read what was written (2x the initial entry).
  VideoDecodeStatsDB::DecodeStatsEntry aggregate_entry(2000, 4, 20);
  EXPECT_CALL(*this, MockGetDecodeStatsCb(true, Pointee(Eq(aggregate_entry))));
  stats_db_->GetDecodeStats(
      key, base::BindOnce(&VideoDecodeStatsDBImplTest::GetDecodeStatsCb,
                          base::Unretained(this)));
  fake_db_->GetCallback(true);

  // Destructively clear all stats from the DB.
  stats_db_->DestroyStats(base::BindOnce(
      &VideoDecodeStatsDBImplTest::MockDestroyStatsCb, base::Unretained(this)));
  fake_db_->DestroyCallback(true);

  // Re-initialize the DB (required) and attempt to re-read previously written
  // stats.
  EXPECT_CALL(*this, OnInitialize(true));
  stats_db_->Initialize(base::BindOnce(
      &VideoDecodeStatsDBImplTest::OnInitialize, base::Unretained(this)));
  fake_db_->InitCallback(true);

  // Database is now empty. Expect null entry.
  EXPECT_CALL(*this, MockGetDecodeStatsCb(true, nullptr));
  stats_db_->GetDecodeStats(
      key, base::BindOnce(&VideoDecodeStatsDBImplTest::GetDecodeStatsCb,
                          base::Unretained(this)));

  fake_db_->GetCallback(true);
}

TEST_F(VideoDecodeStatsDBImplTest, FailedWrite) {
  EXPECT_CALL(*this, OnInitialize(true));
  fake_db_->InitCallback(true);

  VideoDescKey key = VideoDescKey::MakeBucketedKey(VP9PROFILE_PROFILE3,
                                                   gfx::Size(1024, 768), 60);
  VideoDecodeStatsDB::DecodeStatsEntry entry(1000, 2, 10);

  // Expect the callback to indicate success = false when the write fails.
  EXPECT_CALL(*this, MockAppendDecodeStatsCb(false));

  // Append stats, but fail the internal DB update.
  stats_db_->AppendDecodeStats(
      key, entry,
      base::BindOnce(&VideoDecodeStatsDBImplTest::MockAppendDecodeStatsCb,
                     base::Unretained(this)));
  fake_db_->GetCallback(true);
  fake_db_->UpdateCallback(false);

  // Expect the callback to indicate success = false when the write fails
  // because the intermediate "get" (to increment existing counts) has failed.
  EXPECT_CALL(*this, MockAppendDecodeStatsCb(false));

  // Append stats, but fail the internal DB update.
  stats_db_->AppendDecodeStats(
      key, entry,
      base::BindOnce(&VideoDecodeStatsDBImplTest::MockAppendDecodeStatsCb,
                     base::Unretained(this)));
  fake_db_->GetCallback(false);
}

}  // namespace media
