/*
 *  Copyright 2020 The WebRTC Project Authors. All rights reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#include "video/adaptation/pixel_limit_resource.h"

#include <memory>
#include <utility>

#include "api/task_queue/to_queued_task.h"
#include "api/units/timestamp.h"
#include "call/adaptation/test/fake_video_stream_input_state_provider.h"
#include "call/adaptation/test/mock_resource_listener.h"
#include "call/adaptation/video_stream_adapter.h"
#include "rtc_base/task_queue_for_test.h"
#include "test/gmock.h"
#include "test/gtest.h"
#include "test/time_controller/simulated_time_controller.h"

using testing::_;

namespace webrtc {

namespace {

constexpr TimeDelta kResourceUsageCheckIntervalMs = TimeDelta::Seconds(5);

}  // namespace

class PixelLimitResourceTest : public ::testing::Test {
 public:
  PixelLimitResourceTest()
      : time_controller_(Timestamp::Micros(1234)),
        task_queue_(time_controller_.GetTaskQueueFactory()->CreateTaskQueue(
            "TestQueue",
            TaskQueueFactory::Priority::NORMAL)),
        input_state_provider_() {}

  void SetCurrentPixels(int current_pixels) {
    input_state_provider_.SetInputState(current_pixels, 30, current_pixels);
  }

  void RunTaskOnTaskQueue(std::unique_ptr<QueuedTask> task) {
    task_queue_->PostTask(std::move(task));
    time_controller_.AdvanceTime(TimeDelta::Millis(0));
  }

 protected:
  // Posted tasks, including repeated tasks, are executed when simulated time is
  // advanced by time_controller_.AdvanceTime().
  GlobalSimulatedTimeController time_controller_;
  std::unique_ptr<TaskQueueBase, TaskQueueDeleter> task_queue_;
  FakeVideoStreamInputStateProvider input_state_provider_;
};

TEST_F(PixelLimitResourceTest, ResourceIsSilentByDefault) {
  // Because our mock is strick, the test would fail if
  // OnResourceUsageStateMeasured() is invoked.
  testing::StrictMock<MockResourceListener> resource_listener;
  RunTaskOnTaskQueue(ToQueuedTask([&]() {
    rtc::scoped_refptr<PixelLimitResource> pixel_limit_resource =
        PixelLimitResource::Create(task_queue_.get(), &input_state_provider_);
    pixel_limit_resource->SetResourceListener(&resource_listener);
    // Set a current pixel count.
    SetCurrentPixels(1280 * 720);
    // Advance a significant amount of time.
    time_controller_.AdvanceTime(kResourceUsageCheckIntervalMs * 10);
    pixel_limit_resource->SetResourceListener(nullptr);
  }));
}

TEST_F(PixelLimitResourceTest,
       OveruseIsReportedWhileCurrentPixelsIsGreaterThanMaxPixels) {
  constexpr int kMaxPixels = 640 * 480;
  testing::StrictMock<MockResourceListener> resource_listener;
  RunTaskOnTaskQueue(ToQueuedTask([&]() {
    rtc::scoped_refptr<PixelLimitResource> pixel_limit_resource =
        PixelLimitResource::Create(task_queue_.get(), &input_state_provider_);
    pixel_limit_resource->SetResourceListener(&resource_listener);
    time_controller_.AdvanceTime(TimeDelta::Millis(0));

    pixel_limit_resource->SetMaxPixels(kMaxPixels);
    SetCurrentPixels(kMaxPixels + 1);
    EXPECT_CALL(resource_listener,
                OnResourceUsageStateMeasured(_, ResourceUsageState::kOveruse))
        .Times(1);
    time_controller_.AdvanceTime(kResourceUsageCheckIntervalMs);

    // As long as the current pixels has not updated, the overuse signal is
    // repeated at a fixed interval.
    EXPECT_CALL(resource_listener,
                OnResourceUsageStateMeasured(_, ResourceUsageState::kOveruse))
        .Times(3);
    time_controller_.AdvanceTime(kResourceUsageCheckIntervalMs * 3);

    // When the overuse signal has resulted in a lower resolution, the overuse
    // signals stops.
    SetCurrentPixels(kMaxPixels);
    EXPECT_CALL(resource_listener, OnResourceUsageStateMeasured(_, _)).Times(0);
    time_controller_.AdvanceTime(kResourceUsageCheckIntervalMs * 3);

    pixel_limit_resource->SetResourceListener(nullptr);
  }));
}

TEST_F(PixelLimitResourceTest,
       UnderuseIsReportedWhileCurrentPixelsIsLessThanMinPixels) {
  constexpr int kMaxPixels = 640 * 480;
  const int kMinPixels = GetLowerResolutionThan(kMaxPixels);
  testing::StrictMock<MockResourceListener> resource_listener;
  RunTaskOnTaskQueue(ToQueuedTask([&]() {
    rtc::scoped_refptr<PixelLimitResource> pixel_limit_resource =
        PixelLimitResource::Create(task_queue_.get(), &input_state_provider_);
    pixel_limit_resource->SetResourceListener(&resource_listener);
    time_controller_.AdvanceTime(TimeDelta::Millis(0));

    pixel_limit_resource->SetMaxPixels(kMaxPixels);
    SetCurrentPixels(kMinPixels - 1);
    EXPECT_CALL(resource_listener,
                OnResourceUsageStateMeasured(_, ResourceUsageState::kUnderuse))
        .Times(1);
    time_controller_.AdvanceTime(kResourceUsageCheckIntervalMs);

    // As long as the current pixels has not updated, the underuse signal is
    // repeated at a fixed interval.
    EXPECT_CALL(resource_listener,
                OnResourceUsageStateMeasured(_, ResourceUsageState::kUnderuse))
        .Times(3);
    time_controller_.AdvanceTime(kResourceUsageCheckIntervalMs * 3);

    // When the underuse signal has resulted in a higher resolution, the
    // underuse signals stops.
    SetCurrentPixels(kMinPixels);
    EXPECT_CALL(resource_listener, OnResourceUsageStateMeasured(_, _)).Times(0);
    time_controller_.AdvanceTime(kResourceUsageCheckIntervalMs * 3);

    pixel_limit_resource->SetResourceListener(nullptr);
  }));
}

}  // namespace webrtc
