Make the FCUnary class actually work and test it

pull/7018/head
vjpai 9 years ago
parent fcb98a578c
commit c0c38b1f19
  1. 8
      include/grpc++/impl/codegen/completion_queue.h
  2. 19
      include/grpc++/impl/codegen/method_handler_impl.h
  3. 8
      include/grpc++/impl/codegen/server_context.h
  4. 8
      src/compiler/cpp_generator.cc
  5. 39
      test/cpp/end2end/hybrid_end2end_test.cc

@ -59,6 +59,8 @@ template <class W>
class ServerWriter;
template <class W, class R>
class ServerReaderWriter;
template <class Req, class Resp>
class FCUnary;
template <class ServiceType, class RequestType, class ResponseType>
class RpcMethodHandler;
template <class ServiceType, class RequestType, class ResponseType>
@ -67,6 +69,8 @@ template <class ServiceType, class RequestType, class ResponseType>
class ServerStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
class BidiStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
class FCUnaryMethodHandler;
class UnknownMethodHandler;
class Channel;
@ -168,6 +172,8 @@ class CompletionQueue : private GrpcLibraryCodegen {
friend class ::grpc::ServerWriter;
template <class W, class R>
friend class ::grpc::ServerReaderWriter;
template <class Req, class Resp>
friend class ::grpc::FCUnary;
template <class ServiceType, class RequestType, class ResponseType>
friend class RpcMethodHandler;
template <class ServiceType, class RequestType, class ResponseType>
@ -176,6 +182,8 @@ class CompletionQueue : private GrpcLibraryCodegen {
friend class ServerStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
friend class BidiStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
friend class FCUnaryMethodHandler;
friend class UnknownMethodHandler;
friend class ::grpc::Server;
friend class ::grpc::ServerContext;

@ -193,19 +193,22 @@ class BidiStreamingHandler : public MethodHandler {
// A wrapper class of an application provided rpc method handler
// specifically to apply to the flow-controlled implementation of a unary
// method
// method.
/// The argument to the constructor should be a member function already
/// bound to the appropriate service instance. The declaration gets too complicated
/// otherwise.
template <class ServiceType, class RequestType, class ResponseType>
class FCUnaryMethodHandler : public MethodHandler {
public:
FCUnaryMethodHandler(std::function<Status(ServiceType*, ServerContext*,
FCUnaryMethodHandler(std::function<Status(ServerContext*,
FCUnary<RequestType,ResponseType>*)>
func, ServiceType* service)
: func_(func), service_(service) {}
func)
: func_(func) {}
void RunHandler(const HandlerParameter& param) GRPC_FINAL {
FCUnary<RequestType, ResponseType> fc_unary(param.call,
param.server_context);
Status status = func_(service_, param.server_context, &fc_unary);
Status status = func_(param.server_context, &fc_unary);
if (!param.server_context->sent_initial_metadata_) {
// means that the write never happened, which is bad
} else {
@ -216,12 +219,10 @@ class FCUnaryMethodHandler : public MethodHandler {
}
}
private:
// Application provided rpc handler function.
std::function<Status(ServiceType*, ServerContext*,
// Application provided rpc handler function, already bound to its service.
std::function<Status(ServerContext*,
FCUnary<RequestType, ResponseType>*)>
func_;
// The class the above handler function lives in.
ServiceType* service_;
};
// Handle unknown method by returning UNIMPLEMENTED error.

@ -67,6 +67,8 @@ template <class W>
class ServerWriter;
template <class W, class R>
class ServerReaderWriter;
template <class Req, class Resp>
class FCUnary;
template <class ServiceType, class RequestType, class ResponseType>
class RpcMethodHandler;
template <class ServiceType, class RequestType, class ResponseType>
@ -75,6 +77,8 @@ template <class ServiceType, class RequestType, class ResponseType>
class ServerStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
class BidiStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
class FCUnaryMethodHandler;
class UnknownMethodHandler;
class Call;
@ -177,6 +181,8 @@ class ServerContext {
friend class ::grpc::ServerWriter;
template <class W, class R>
friend class ::grpc::ServerReaderWriter;
template <class Req, class Resp>
friend class ::grpc::FCUnary;
template <class ServiceType, class RequestType, class ResponseType>
friend class RpcMethodHandler;
template <class ServiceType, class RequestType, class ResponseType>
@ -185,6 +191,8 @@ class ServerContext {
friend class ServerStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
friend class BidiStreamingHandler;
template <class ServiceType, class RequestType, class ResponseType>
friend class FCUnaryMethodHandler;
friend class UnknownMethodHandler;
friend class ::grpc::ClientContext;

@ -626,11 +626,11 @@ void PrintHeaderServerMethodFCUnary(
printer->Indent();
printer->Print(*vars,
"WithFCUnaryMethod_$Method$() {\n"
" ::grpc::Status (*fn)(::grpc::ServerContext*, ::grpc::FCUnary< $Request$,$Response$>*) = this->WithFCUnaryMethod_$Method$<BaseClass>::$Method$;\n"
" ::grpc::Service::MarkMethodFCUnary($Idx$,\n"
" new ::grpc::FCUnaryMethodHandler<Service, "
"$Request$, "
"$Response$>(fn, this));\n"
"$Response$>("
"std::bind(&WithFCUnaryMethod_$Method$<BaseClass>::FC$Method$, this, std::placeholders::_1, std::placeholders::_2)));\n"
"}\n");
printer->Print(*vars,
"~WithFCUnaryMethod_$Method$() GRPC_OVERRIDE {\n"
@ -648,9 +648,9 @@ void PrintHeaderServerMethodFCUnary(
printer->Print(
*vars,
"// replace default version of this method with FCUnary\n"
"::grpc::Status $Method$("
"virtual ::grpc::Status FC$Method$("
"::grpc::ServerContext* context, ::grpc::FCUnary< $Request$,$Response$>* fc_unary)"
" GRPC_FINAL GRPC_OVERRIDE;\n");
" = 0;\n");
printer->Outdent();
printer->Print(*vars, "};\n");
}

@ -199,7 +199,7 @@ class HybridEnd2endTest : public ::testing::Test {
HybridEnd2endTest() {}
void SetUpServer(::grpc::Service* service1, ::grpc::Service* service2,
AsyncGenericService* generic_service) {
AsyncGenericService* generic_service, int max_message_size = 0) {
int port = grpc_pick_unused_port_or_die();
server_address_ << "localhost:" << port;
@ -217,6 +217,11 @@ class HybridEnd2endTest : public ::testing::Test {
if (generic_service) {
builder.RegisterAsyncGenericService(generic_service);
}
if (max_message_size != 0) {
builder.SetMaxMessageSize(max_message_size);
}
// Create a separate cq for each potential handler.
for (int i = 0; i < 5; i++) {
cqs_.push_back(builder.AddCompletionQueue(false));
@ -415,6 +420,38 @@ TEST_F(HybridEnd2endTest, AsyncRequestStreamResponseStream_SyncDupService) {
request_stream_handler_thread.join();
}
// Add a second service with one sync FCUnary method.
class FCUnaryDupPkg : public duplicate::EchoTestService::WithFCUnaryMethod_Echo<TestServiceImplDupPkg> {
public:
Status FCEcho(ServerContext* context, FCUnary<EchoRequest,EchoResponse>* fc_unary) GRPC_OVERRIDE {
EchoRequest req;
EchoResponse resp;
gpr_log(GPR_INFO, "FC Unary Next Message Size is %u", fc_unary->NextMessageSize());
GPR_ASSERT(fc_unary->Read(&req));
resp.set_message(req.message() + "_dup");
GPR_ASSERT(fc_unary->Write(resp));
return Status::OK;
}
};
TEST_F(HybridEnd2endTest, AsyncRequestStreamResponseStream_SyncFCUnaryDupService) {
typedef EchoTestService::WithAsyncMethod_RequestStream<
EchoTestService::WithAsyncMethod_ResponseStream<TestServiceImpl>>
SType;
SType service;
FCUnaryDupPkg dup_service;
SetUpServer(&service, &dup_service, nullptr, 8192);
ResetStub();
std::thread response_stream_handler_thread(HandleServerStreaming<SType>,
&service, cqs_[0].get());
std::thread request_stream_handler_thread(HandleClientStreaming<SType>,
&service, cqs_[1].get());
TestAllMethods();
SendEchoToDupService();
response_stream_handler_thread.join();
request_stream_handler_thread.join();
}
// Add a second service with one async method.
TEST_F(HybridEnd2endTest, AsyncRequestStreamResponseStream_AsyncDupService) {
typedef EchoTestService::WithAsyncMethod_RequestStream<

Loading…
Cancel
Save