// WARNING: This file is machine generated by fidlgen.

// fidl_experiment = output_index_json

#pragma once

#include <fidl/test.unknowninteractions/cpp/wire.h>

#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wshadow"

namespace fidl {
namespace testing {

template <>
class WireTestBase<::test_unknowninteractions::UnknownInteractionsProtocol> : public ::fidl::WireServer<::test_unknowninteractions::UnknownInteractionsProtocol> {
 public:
  virtual ~WireTestBase<::test_unknowninteractions::UnknownInteractionsProtocol>() = default;
  virtual void NotImplemented_(const std::string& name, ::fidl::CompleterBase& completer) = 0;
  virtual void StrictOneWay(
      StrictOneWayCompleter::Sync& completer) override {
    NotImplemented_("StrictOneWay", completer);
  }
  virtual void FlexibleOneWay(
      FlexibleOneWayCompleter::Sync& completer) override {
    NotImplemented_("FlexibleOneWay", completer);
  }
  virtual void StrictTwoWay(
      StrictTwoWayCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWay", completer);
  }
  virtual void StrictTwoWayFields(
      StrictTwoWayFieldsCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayFields", completer);
  }
  virtual void StrictTwoWayUnion(
      StrictTwoWayUnionCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayUnion", completer);
  }
  virtual void StrictTwoWayTable(
      StrictTwoWayTableCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayTable", completer);
  }
  virtual void StrictTwoWayErr(
      StrictTwoWayErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayErr", completer);
  }
  virtual void StrictTwoWayFieldsErr(
      StrictTwoWayFieldsErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayFieldsErr", completer);
  }
  virtual void StrictTwoWayUnionErr(
      StrictTwoWayUnionErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayUnionErr", completer);
  }
  virtual void StrictTwoWayTableErr(
      StrictTwoWayTableErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayTableErr", completer);
  }
  virtual void FlexibleTwoWay(
      FlexibleTwoWayCompleter::Sync& completer) override {
    NotImplemented_("FlexibleTwoWay", completer);
  }
  virtual void FlexibleTwoWayFields(
      FlexibleTwoWayFieldsCompleter::Sync& completer) override {
    NotImplemented_("FlexibleTwoWayFields", completer);
  }
  virtual void FlexibleTwoWayUnion(
      FlexibleTwoWayUnionCompleter::Sync& completer) override {
    NotImplemented_("FlexibleTwoWayUnion", completer);
  }
  virtual void FlexibleTwoWayTable(
      FlexibleTwoWayTableCompleter::Sync& completer) override {
    NotImplemented_("FlexibleTwoWayTable", completer);
  }
  virtual void FlexibleTwoWayErr(
      FlexibleTwoWayErrCompleter::Sync& completer) override {
    NotImplemented_("FlexibleTwoWayErr", completer);
  }
  virtual void FlexibleTwoWayFieldsErr(
      FlexibleTwoWayFieldsErrCompleter::Sync& completer) override {
    NotImplemented_("FlexibleTwoWayFieldsErr", completer);
  }
  virtual void FlexibleTwoWayUnionErr(
      FlexibleTwoWayUnionErrCompleter::Sync& completer) override {
    NotImplemented_("FlexibleTwoWayUnionErr", completer);
  }
  virtual void FlexibleTwoWayTableErr(
      FlexibleTwoWayTableErrCompleter::Sync& completer) override {
    NotImplemented_("FlexibleTwoWayTableErr", completer);
  }
  virtual void handle_unknown_method(::fidl::UnknownMethodMetadata<::test_unknowninteractions::UnknownInteractionsProtocol> metadata, UnknownMethodCompleter::Sync& completer) override {
    NotImplemented_("handle_unknown_method", completer);
  }
};

template <>
class WireSyncEventHandlerTestBase<::test_unknowninteractions::UnknownInteractionsProtocol> : public ::fidl::WireSyncEventHandler<::test_unknowninteractions::UnknownInteractionsProtocol> {
 public:
  virtual ~WireSyncEventHandlerTestBase<::test_unknowninteractions::UnknownInteractionsProtocol>() = default;
  virtual void NotImplemented_(const std::string& name) = 0;
  void StrictEvent() override {
    NotImplemented_("StrictEvent");
  }
  void StrictEventFields(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsProtocol::StrictEventFields>* event) override {
    NotImplemented_("StrictEventFields");
  }
  void StrictEventUnion(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsProtocol::StrictEventUnion>* event) override {
    NotImplemented_("StrictEventUnion");
  }
  void StrictEventTable(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsProtocol::StrictEventTable>* event) override {
    NotImplemented_("StrictEventTable");
  }
  void FlexibleEvent() override {
    NotImplemented_("FlexibleEvent");
  }
  void FlexibleEventFields(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsProtocol::FlexibleEventFields>* event) override {
    NotImplemented_("FlexibleEventFields");
  }
  void FlexibleEventUnion(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsProtocol::FlexibleEventUnion>* event) override {
    NotImplemented_("FlexibleEventUnion");
  }
  void FlexibleEventTable(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsProtocol::FlexibleEventTable>* event) override {
    NotImplemented_("FlexibleEventTable");
  }
  virtual void handle_unknown_event(::fidl::UnknownEventMetadata<::test_unknowninteractions::UnknownInteractionsProtocol> metadata) override {
    NotImplemented_("handle_unknown_event");
  }
};

template <>
class WireTestBase<::test_unknowninteractions::UnknownInteractionsAjarProtocol> : public ::fidl::WireServer<::test_unknowninteractions::UnknownInteractionsAjarProtocol> {
 public:
  virtual ~WireTestBase<::test_unknowninteractions::UnknownInteractionsAjarProtocol>() = default;
  virtual void NotImplemented_(const std::string& name, ::fidl::CompleterBase& completer) = 0;
  virtual void StrictOneWay(
      StrictOneWayCompleter::Sync& completer) override {
    NotImplemented_("StrictOneWay", completer);
  }
  virtual void FlexibleOneWay(
      FlexibleOneWayCompleter::Sync& completer) override {
    NotImplemented_("FlexibleOneWay", completer);
  }
  virtual void StrictTwoWay(
      StrictTwoWayCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWay", completer);
  }
  virtual void StrictTwoWayFields(
      StrictTwoWayFieldsCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayFields", completer);
  }
  virtual void StrictTwoWayUnion(
      StrictTwoWayUnionCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayUnion", completer);
  }
  virtual void StrictTwoWayTable(
      StrictTwoWayTableCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayTable", completer);
  }
  virtual void StrictTwoWayErr(
      StrictTwoWayErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayErr", completer);
  }
  virtual void StrictTwoWayFieldsErr(
      StrictTwoWayFieldsErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayFieldsErr", completer);
  }
  virtual void StrictTwoWayUnionErr(
      StrictTwoWayUnionErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayUnionErr", completer);
  }
  virtual void StrictTwoWayTableErr(
      StrictTwoWayTableErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayTableErr", completer);
  }
  virtual void handle_unknown_method(::fidl::UnknownMethodMetadata<::test_unknowninteractions::UnknownInteractionsAjarProtocol> metadata, UnknownMethodCompleter::Sync& completer) override {
    NotImplemented_("handle_unknown_method", completer);
  }
};

template <>
class WireSyncEventHandlerTestBase<::test_unknowninteractions::UnknownInteractionsAjarProtocol> : public ::fidl::WireSyncEventHandler<::test_unknowninteractions::UnknownInteractionsAjarProtocol> {
 public:
  virtual ~WireSyncEventHandlerTestBase<::test_unknowninteractions::UnknownInteractionsAjarProtocol>() = default;
  virtual void NotImplemented_(const std::string& name) = 0;
  void StrictEvent() override {
    NotImplemented_("StrictEvent");
  }
  void StrictEventFields(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsAjarProtocol::StrictEventFields>* event) override {
    NotImplemented_("StrictEventFields");
  }
  void StrictEventUnion(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsAjarProtocol::StrictEventUnion>* event) override {
    NotImplemented_("StrictEventUnion");
  }
  void StrictEventTable(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsAjarProtocol::StrictEventTable>* event) override {
    NotImplemented_("StrictEventTable");
  }
  void FlexibleEvent() override {
    NotImplemented_("FlexibleEvent");
  }
  void FlexibleEventFields(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsAjarProtocol::FlexibleEventFields>* event) override {
    NotImplemented_("FlexibleEventFields");
  }
  void FlexibleEventUnion(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsAjarProtocol::FlexibleEventUnion>* event) override {
    NotImplemented_("FlexibleEventUnion");
  }
  void FlexibleEventTable(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsAjarProtocol::FlexibleEventTable>* event) override {
    NotImplemented_("FlexibleEventTable");
  }
  virtual void handle_unknown_event(::fidl::UnknownEventMetadata<::test_unknowninteractions::UnknownInteractionsAjarProtocol> metadata) override {
    NotImplemented_("handle_unknown_event");
  }
};

template <>
class WireTestBase<::test_unknowninteractions::UnknownInteractionsClosedProtocol> : public ::fidl::WireServer<::test_unknowninteractions::UnknownInteractionsClosedProtocol> {
 public:
  virtual ~WireTestBase<::test_unknowninteractions::UnknownInteractionsClosedProtocol>() = default;
  virtual void NotImplemented_(const std::string& name, ::fidl::CompleterBase& completer) = 0;
  virtual void StrictOneWay(
      StrictOneWayCompleter::Sync& completer) override {
    NotImplemented_("StrictOneWay", completer);
  }
  virtual void StrictTwoWay(
      StrictTwoWayCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWay", completer);
  }
  virtual void StrictTwoWayFields(
      StrictTwoWayFieldsCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayFields", completer);
  }
  virtual void StrictTwoWayUnion(
      StrictTwoWayUnionCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayUnion", completer);
  }
  virtual void StrictTwoWayTable(
      StrictTwoWayTableCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayTable", completer);
  }
  virtual void StrictTwoWayErr(
      StrictTwoWayErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayErr", completer);
  }
  virtual void StrictTwoWayFieldsErr(
      StrictTwoWayFieldsErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayFieldsErr", completer);
  }
  virtual void StrictTwoWayUnionErr(
      StrictTwoWayUnionErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayUnionErr", completer);
  }
  virtual void StrictTwoWayTableErr(
      StrictTwoWayTableErrCompleter::Sync& completer) override {
    NotImplemented_("StrictTwoWayTableErr", completer);
  }
};

template <>
class WireSyncEventHandlerTestBase<::test_unknowninteractions::UnknownInteractionsClosedProtocol> : public ::fidl::WireSyncEventHandler<::test_unknowninteractions::UnknownInteractionsClosedProtocol> {
 public:
  virtual ~WireSyncEventHandlerTestBase<::test_unknowninteractions::UnknownInteractionsClosedProtocol>() = default;
  virtual void NotImplemented_(const std::string& name) = 0;
  void StrictEvent() override {
    NotImplemented_("StrictEvent");
  }
  void StrictEventFields(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsClosedProtocol::StrictEventFields>* event) override {
    NotImplemented_("StrictEventFields");
  }
  void StrictEventUnion(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsClosedProtocol::StrictEventUnion>* event) override {
    NotImplemented_("StrictEventUnion");
  }
  void StrictEventTable(::fidl::WireEvent<::test_unknowninteractions::UnknownInteractionsClosedProtocol::StrictEventTable>* event) override {
    NotImplemented_("StrictEventTable");
  }
};
#pragma clang diagnostic pop

}  // namespace testing
}  // namespace fidl
