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

#ifndef MEDIA_AUDIO_AUDIO_SYSTEM_TEST_UTIL_H_
#define MEDIA_AUDIO_AUDIO_SYSTEM_TEST_UTIL_H_

#include "base/bind.h"
#include "base/location.h"
#include "base/macros.h"
#include "base/message_loop/message_loop.h"
#include "base/optional.h"
#include "base/run_loop.h"
#include "base/threading/thread_checker.h"
#include "media/audio/audio_device_description.h"
#include "media/audio/audio_system.h"
#include "media/audio/mock_audio_manager.h"
#include "media/base/audio_parameters.h"
#include "testing/gmock/include/gmock/gmock.h"

namespace media {

// For tests only. Creates AudioSystem callbacks to be passed to AudioSystem
// methods. When AudioSystem calls such a callback, it verifies treading
// expectations and checks recieved parameters against expected values passed
// during its creation. After that it calls |on_cb_received| closure.
// Note AudioSystemCallbackExpectations object must outlive all the callbacks
// it produced, since they contain raw pointers to it.
class AudioSystemCallbackExpectations {
 public:
  AudioSystemCallbackExpectations() = default;
  AudioSystem::OnAudioParamsCallback GetAudioParamsCallback(
      const base::Location& location,
      base::OnceClosure on_cb_received,
      const base::Optional<AudioParameters>& expected_params);

  AudioSystem::OnBoolCallback GetBoolCallback(const base::Location& location,
                                              base::OnceClosure on_cb_received,
                                              bool expected);

  AudioSystem::OnDeviceDescriptionsCallback GetDeviceDescriptionsCallback(
      const base::Location& location,
      base::OnceClosure on_cb_received,
      const AudioDeviceDescriptions& expected_descriptions);

  AudioSystem::OnInputDeviceInfoCallback GetInputDeviceInfoCallback(
      const base::Location& location,
      base::OnceClosure on_cb_received,
      const base::Optional<AudioParameters>& expected_input,
      const base::Optional<AudioParameters>& expected_associated_output,
      const std::string& expected_associated_device_id);

  AudioSystem::OnDeviceIdCallback GetDeviceIdCallback(
      const base::Location& location,
      base::OnceClosure on_cb_received,
      const std::string& expected_id);

 private:
  // Methods to verify correctness of received data.
  void OnAudioParams(const std::string& from_here,
                     base::OnceClosure on_cb_received,
                     const base::Optional<AudioParameters>& expected,
                     const base::Optional<AudioParameters>& received);

  void OnBool(const std::string& from_here,
              base::OnceClosure on_cb_received,
              bool expected,
              bool result);

  void OnDeviceDescriptions(
      const std::string& from_here,
      base::OnceClosure on_cb_received,
      const AudioDeviceDescriptions& expected_descriptions,
      AudioDeviceDescriptions descriptions);

  void OnInputDeviceInfo(
      const std::string& from_here,
      base::OnceClosure on_cb_received,
      const base::Optional<AudioParameters>& expected_input,
      const base::Optional<AudioParameters>& expected_associated_output,
      const std::string& expected_associated_device_id,
      const base::Optional<AudioParameters>& input,
      const base::Optional<AudioParameters>& associated_output,
      const std::string& associated_device_id);

  void OnDeviceId(const std::string& from_here,
                  base::OnceClosure on_cb_received,
                  const std::string& expected_id,
                  const std::string& result_id);

  THREAD_CHECKER(thread_checker_);
  DISALLOW_COPY_AND_ASSIGN(AudioSystemCallbackExpectations);
};

// Template test case to test AudioSystem implementations.
template <class T>
class AudioSystemTestTemplate : public T {
 public:
  AudioSystemTestTemplate() {}
  ~AudioSystemTestTemplate() override {}

  void SetUp() override {
    T::SetUp();
    input_params_ =
        AudioParameters(AudioParameters::AUDIO_PCM_LINEAR, CHANNEL_LAYOUT_MONO,
                        AudioParameters::kTelephoneSampleRate, 16,
                        AudioParameters::kTelephoneSampleRate / 10);
    output_params_ =
        AudioParameters(AudioParameters::AUDIO_PCM_LINEAR, CHANNEL_LAYOUT_MONO,
                        AudioParameters::kTelephoneSampleRate, 16,
                        AudioParameters::kTelephoneSampleRate / 20);
    default_output_params_ =
        AudioParameters(AudioParameters::AUDIO_PCM_LINEAR, CHANNEL_LAYOUT_MONO,
                        AudioParameters::kTelephoneSampleRate, 16,
                        AudioParameters::kTelephoneSampleRate / 30);
    audio_manager()->SetInputStreamParameters(input_params_);
    audio_manager()->SetOutputStreamParameters(output_params_);
    audio_manager()->SetDefaultOutputStreamParameters(default_output_params_);

    auto get_device_descriptions = [](const AudioDeviceDescriptions* source,
                                      AudioDeviceDescriptions* destination) {
      destination->insert(destination->end(), source->begin(), source->end());
    };

    audio_manager()->SetInputDeviceDescriptionsCallback(
        base::Bind(get_device_descriptions,
                   base::Unretained(&input_device_descriptions_)));
    audio_manager()->SetOutputDeviceDescriptionsCallback(
        base::Bind(get_device_descriptions,
                   base::Unretained(&output_device_descriptions_)));
  }

 protected:
  MockAudioManager* audio_manager() { return T::audio_manager(); }
  AudioSystem* audio_system() { return T::audio_system(); }

  AudioSystemCallbackExpectations expectations_;
  AudioParameters input_params_;
  AudioParameters output_params_;
  AudioParameters default_output_params_;
  AudioDeviceDescriptions input_device_descriptions_;
  AudioDeviceDescriptions output_device_descriptions_;

 private:
  DISALLOW_COPY_AND_ASSIGN(AudioSystemTestTemplate);
};

TYPED_TEST_CASE_P(AudioSystemTestTemplate);

TYPED_TEST_P(AudioSystemTestTemplate, GetInputStreamParametersNormal) {
  base::RunLoop wait_loop;
  this->audio_system()->GetInputStreamParameters(
      AudioDeviceDescription::kDefaultDeviceId,
      this->expectations_.GetAudioParamsCallback(
          FROM_HERE, wait_loop.QuitClosure(), this->input_params_));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, GetInputStreamParametersNoDevice) {
  this->audio_manager()->SetHasInputDevices(false);

  base::RunLoop wait_loop;
  this->audio_system()->GetInputStreamParameters(
      AudioDeviceDescription::kDefaultDeviceId,
      this->expectations_.GetAudioParamsCallback(
          FROM_HERE, wait_loop.QuitClosure(),
          base::Optional<AudioParameters>()));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, GetOutputStreamParameters) {
  base::RunLoop wait_loop;
  this->audio_system()->GetOutputStreamParameters(
      "non-default-device-id",
      this->expectations_.GetAudioParamsCallback(
          FROM_HERE, wait_loop.QuitClosure(), this->output_params_));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, GetDefaultOutputStreamParameters) {
  base::RunLoop wait_loop;
  this->audio_system()->GetOutputStreamParameters(
      AudioDeviceDescription::kDefaultDeviceId,
      this->expectations_.GetAudioParamsCallback(
          FROM_HERE, wait_loop.QuitClosure(), this->default_output_params_));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate,
             GetOutputStreamParametersForDefaultDeviceNoDevices) {
  this->audio_manager()->SetHasOutputDevices(false);
  base::RunLoop wait_loop;
  this->audio_system()->GetOutputStreamParameters(
      AudioDeviceDescription::kDefaultDeviceId,
      this->expectations_.GetAudioParamsCallback(
          FROM_HERE, wait_loop.QuitClosure(),
          base::Optional<AudioParameters>()));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate,
             GetOutputStreamParametersForNonDefaultDeviceNoDevices) {
  this->audio_manager()->SetHasOutputDevices(false);
  base::RunLoop wait_loop;
  this->audio_system()->GetOutputStreamParameters(
      "non-default-device-id", this->expectations_.GetAudioParamsCallback(
                                   FROM_HERE, wait_loop.QuitClosure(),
                                   base::Optional<AudioParameters>()));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, HasInputDevices) {
  base::RunLoop wait_loop;
  this->audio_system()->HasInputDevices(this->expectations_.GetBoolCallback(
      FROM_HERE, wait_loop.QuitClosure(), true));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, HasNoInputDevices) {
  this->audio_manager()->SetHasInputDevices(false);
  base::RunLoop wait_loop;
  this->audio_system()->HasInputDevices(this->expectations_.GetBoolCallback(
      FROM_HERE, wait_loop.QuitClosure(), false));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, HasOutputDevices) {
  base::RunLoop wait_loop;
  this->audio_system()->HasOutputDevices(this->expectations_.GetBoolCallback(
      FROM_HERE, wait_loop.QuitClosure(), true));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, HasNoOutputDevices) {
  this->audio_manager()->SetHasOutputDevices(false);
  base::RunLoop wait_loop;
  this->audio_system()->HasOutputDevices(this->expectations_.GetBoolCallback(
      FROM_HERE, wait_loop.QuitClosure(), false));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate,
             GetInputDeviceDescriptionsNoInputDevices) {
  this->output_device_descriptions_.emplace_back(
      "output_device_name", "output_device_id", "group_id");
  EXPECT_EQ(0, static_cast<int>(this->input_device_descriptions_.size()));
  EXPECT_EQ(1, static_cast<int>(this->output_device_descriptions_.size()));

  base::RunLoop wait_loop;
  this->audio_system()->GetDeviceDescriptions(
      true, this->expectations_.GetDeviceDescriptionsCallback(
                FROM_HERE, wait_loop.QuitClosure(),
                this->input_device_descriptions_));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, GetInputDeviceDescriptions) {
  this->output_device_descriptions_.emplace_back(
      "output_device_name", "output_device_id", "group_id");
  this->input_device_descriptions_.emplace_back(
      "input_device_name1", "input_device_id1", "group_id1");
  this->input_device_descriptions_.emplace_back(
      "input_device_name2", "input_device_id2", "group_id2");
  EXPECT_EQ(2, static_cast<int>(this->input_device_descriptions_.size()));
  EXPECT_EQ(1, static_cast<int>(this->output_device_descriptions_.size()));

  base::RunLoop wait_loop;
  this->audio_system()->GetDeviceDescriptions(
      true, this->expectations_.GetDeviceDescriptionsCallback(
                FROM_HERE, wait_loop.QuitClosure(),
                this->input_device_descriptions_));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate,
             GetOutputDeviceDescriptionsNoInputDevices) {
  this->input_device_descriptions_.emplace_back("input_device_name",
                                                "input_device_id", "group_id");
  EXPECT_EQ(0, static_cast<int>(this->output_device_descriptions_.size()));
  EXPECT_EQ(1, static_cast<int>(this->input_device_descriptions_.size()));

  base::RunLoop wait_loop;
  this->audio_system()->GetDeviceDescriptions(
      false, this->expectations_.GetDeviceDescriptionsCallback(
                 FROM_HERE, wait_loop.QuitClosure(),
                 this->output_device_descriptions_));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, GetOutputDeviceDescriptions) {
  this->input_device_descriptions_.emplace_back("input_device_name",
                                                "input_device_id", "group_id");
  this->output_device_descriptions_.emplace_back(
      "output_device_name1", "output_device_id1", "group_id1");
  this->output_device_descriptions_.emplace_back(
      "output_device_name2", "output_device_id2", "group_id2");
  EXPECT_EQ(2, static_cast<int>(this->output_device_descriptions_.size()));
  EXPECT_EQ(1, static_cast<int>(this->input_device_descriptions_.size()));

  base::RunLoop wait_loop;
  this->audio_system()->GetDeviceDescriptions(
      false, this->expectations_.GetDeviceDescriptionsCallback(
                 FROM_HERE, wait_loop.QuitClosure(),
                 this->output_device_descriptions_));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, GetAssociatedOutputDeviceID) {
  const std::string associated_id("associated_id");
  this->audio_manager()->SetAssociatedOutputDeviceIDCallback(
      base::Bind([](const std::string& result,
                    const std::string&) -> std::string { return result; },
                 associated_id));

  base::RunLoop wait_loop;
  this->audio_system()->GetAssociatedOutputDeviceID(
      std::string(), this->expectations_.GetDeviceIdCallback(
                         FROM_HERE, wait_loop.QuitClosure(), associated_id));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, GetInputDeviceInfoNoAssociation) {
  base::RunLoop wait_loop;
  this->audio_system()->GetInputDeviceInfo(
      "non-default-device-id",
      this->expectations_.GetInputDeviceInfoCallback(
          FROM_HERE, wait_loop.QuitClosure(), this->input_params_,
          base::Optional<AudioParameters>(), std::string()));
  wait_loop.Run();
}

TYPED_TEST_P(AudioSystemTestTemplate, GetInputDeviceInfoWithAssociation) {
  const std::string associated_id("associated_id");
  this->audio_manager()->SetAssociatedOutputDeviceIDCallback(
      base::Bind([](const std::string& result,
                    const std::string&) -> std::string { return result; },
                 associated_id));

  base::RunLoop wait_loop;
  this->audio_system()->GetInputDeviceInfo(
      "non-default-device-id",
      this->expectations_.GetInputDeviceInfoCallback(
          FROM_HERE, wait_loop.QuitClosure(), this->input_params_,
          this->output_params_, associated_id));
  wait_loop.Run();
}

REGISTER_TYPED_TEST_CASE_P(
    AudioSystemTestTemplate,
    GetInputStreamParametersNormal,
    GetInputStreamParametersNoDevice,
    GetOutputStreamParameters,
    GetDefaultOutputStreamParameters,
    GetOutputStreamParametersForDefaultDeviceNoDevices,
    GetOutputStreamParametersForNonDefaultDeviceNoDevices,
    HasInputDevices,
    HasNoInputDevices,
    HasOutputDevices,
    HasNoOutputDevices,
    GetInputDeviceDescriptionsNoInputDevices,
    GetInputDeviceDescriptions,
    GetOutputDeviceDescriptionsNoInputDevices,
    GetOutputDeviceDescriptions,
    GetAssociatedOutputDeviceID,
    GetInputDeviceInfoNoAssociation,
    GetInputDeviceInfoWithAssociation);

}  // namespace media

#endif  // MEDIA_AUDIO_AUDIO_SYSTEM_TEST_UTIL_H_
