// Copyright 2019 The Fuchsia 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 LIB_SYS_CPP_TESTING_COMPONENT_CONTEXT_PROVIDER_H_
#define LIB_SYS_CPP_TESTING_COMPONENT_CONTEXT_PROVIDER_H_

#include <lib/fdio/directory.h>
#include <lib/sys/cpp/component_context.h>
#include <lib/sys/cpp/testing/service_directory_provider.h>

namespace sys {
namespace testing {

// Provides fake |ComponentContext| for unit testing.
// Provides access to services that have been added to this object.
// The object of this class should be kept alive for fake |ComponentContext| to
// work.
//
// This class is thread-hostile.
//
//  # Simple usage
//
// Instances of this class should be owned and managed on the same thread.
//
// # Advanced usage
//
// You can use a background thread to service this class provided:
// async_dispatcher_t for the background thread is stopped or suspended
// prior to destroying the class object.
class ComponentContextProvider {
 public:
  explicit ComponentContextProvider(async_dispatcher_t* dispatcher = nullptr);

  ~ComponentContextProvider();

  // Points to outgoing root directory of outgoing directory, test can get it
  // and try to connect to internal directories/objects/files/services to test
  // code which published them.
  fuchsia::io::DirectoryPtr& outgoing_directory_ptr() {
    return outgoing_directory_ptr_;
  }

  // Connects to public service which was published in "public" directory by
  // code under test.
  template <typename Interface>
  fidl::InterfacePtr<Interface> ConnectToPublicService(
      const std::string& name = Interface::Name_,
      async_dispatcher_t* dispatcher = nullptr) const {
    fidl::InterfacePtr<Interface> ptr;
    ConnectToPublicService(ptr.NewRequest(dispatcher), name);
    return ptr;
  }

  // Connects to public service which was published in "public" directory by
  // code under test.
  template <typename Interface>
  void ConnectToPublicService(
      fidl::InterfaceRequest<Interface> request,
      const std::string& name = Interface::Name_) const {
    fdio_service_connect_at(public_directory_ptr_.channel().get(), name.c_str(),
                            request.TakeChannel().release());
  }

  // Gets a fake service directory that can be used to inject services
  // which can be accessed by code under test.
  //
  // # Example
  //
  // ```
  // fidl::BindingSet<fuchsia::foo::Controller> bindings;
  // context_provider->service_directory_provider()->AddService(bindings.GetHandler(this));
  // auto context = context_provider->context();
  // ...
  // ...
  // ...
  // context->svc()->Connect(...);
  // ```
  const std::shared_ptr<ServiceDirectoryProvider>& service_directory_provider()
      const {
    return svc_provider_;
  }

  // Relinquishes the ownership of fake context. This object should be alive
  // for lifetime of returned context.
  std::unique_ptr<sys::ComponentContext> TakeContext() {
    return std::move(component_context_);
  }

  sys::ComponentContext* context() { return component_context_.get(); }

 private:
  fuchsia::io::DirectoryPtr outgoing_directory_ptr_;
  fuchsia::io::DirectoryPtr public_directory_ptr_;
  std::shared_ptr<ServiceDirectoryProvider> svc_provider_;
  std::unique_ptr<sys::ComponentContext> component_context_;
};

}  // namespace testing
}  // namespace sys

#endif  // LIB_SYS_CPP_TESTING_COMPONENT_CONTEXT_PROVIDER_H_
