diff --git a/src/compiler/csharp_generator.cc b/src/compiler/csharp_generator.cc index fb11d98fe47..bc40880e5ca 100644 --- a/src/compiler/csharp_generator.cc +++ b/src/compiler/csharp_generator.cc @@ -73,10 +73,6 @@ std::string GetClientInterfaceName(const ServiceDescriptor* service) { return "I" + service->name() + "Client"; } -std::string GetClientBaseClassName(const ServiceDescriptor* service) { - return service->name() + "ClientBase"; -} - std::string GetClientClassName(const ServiceDescriptor* service) { return service->name() + "Client"; } @@ -300,86 +296,6 @@ void GenerateClientInterface(Printer* out, const ServiceDescriptor *service) { out->Print("\n"); } -void GenerateClientBaseClass(Printer* out, const ServiceDescriptor *service) { - out->Print("// abstract client class\n"); - out->Print("public abstract class $name$ : ClientBase\n", "name", - GetClientBaseClassName(service)); - out->Print("{\n"); - out->Indent(); - - // constructors - out->Print( - "public $name$(Channel channel) : base(channel)\n", - "name", GetClientBaseClassName(service)); - out->Print("{\n"); - out->Print("}\n"); - - for (int i = 0; i < service->method_count(); i++) { - const MethodDescriptor *method = service->method(i); - MethodType method_type = GetMethodType(method); - - if (method_type == METHODTYPE_NO_STREAMING) { - // unary calls have an extra synchronous stub method - out->Print( - "public virtual $response$ $methodname$($request$ request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken))\n", - "methodname", method->name(), "request", - GetClassName(method->input_type()), "response", - GetClassName(method->output_type())); - out->Print("{\n"); - out->Indent(); - out->Print("return $methodname$(request, new CallOptions(headers, deadline, cancellationToken));\n", - "methodname", method->name()); - out->Outdent(); - out->Print("}\n"); - - // overload taking CallOptions as a param - out->Print( - "public virtual $response$ $methodname$($request$ request, CallOptions options)\n", - "methodname", method->name(), "request", - GetClassName(method->input_type()), "response", - GetClassName(method->output_type())); - out->Print("{\n"); - out->Indent(); - out->Print("throw new NotImplementedException();\n"); - out->Outdent(); - out->Print("}\n"); - } - - std::string method_name = method->name(); - if (method_type == METHODTYPE_NO_STREAMING) { - method_name += "Async"; // prevent name clash with synchronous method. - } - out->Print( - "public virtual $returntype$ $methodname$($request_maybe$Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken))\n", - "methodname", method_name, "request_maybe", - GetMethodRequestParamMaybe(method), "returntype", - GetMethodReturnTypeClient(method)); - out->Print("{\n"); - out->Indent(); - - out->Print("return $methodname$($request_maybe$new CallOptions(headers, deadline, cancellationToken));\n", - "methodname", method_name, - "request_maybe", GetMethodRequestParamMaybe(method, true)); - out->Outdent(); - out->Print("}\n"); - - // overload taking CallOptions as a param - out->Print( - "public virtual $returntype$ $methodname$($request_maybe$CallOptions options)\n", - "methodname", method_name, "request_maybe", - GetMethodRequestParamMaybe(method), "returntype", - GetMethodReturnTypeClient(method)); - out->Print("{\n"); - out->Indent(); - out->Print("throw new NotImplementedException();\n"); - out->Outdent(); - out->Print("}\n"); - } - out->Outdent(); - out->Print("}\n"); - out->Print("\n"); -} - void GenerateServerInterface(Printer* out, const ServiceDescriptor *service) { out->Print("// server-side interface\n"); out->Print("[System.Obsolete(\"Service implementations should inherit" @@ -433,18 +349,20 @@ void GenerateServerClass(Printer* out, const ServiceDescriptor *service) { void GenerateClientStub(Printer* out, const ServiceDescriptor *service) { out->Print("// client stub\n"); out->Print( - "public class $name$ : $baseclass$\n", - "name", GetClientClassName(service), - "baseclass", GetClientBaseClassName(service)); + "public class $name$ : ClientBase<$name$>\n", + "name", GetClientClassName(service)); out->Print("{\n"); out->Indent(); // constructors - out->Print( - "public $name$(Channel channel) : base(channel)\n", - "name", GetClientClassName(service)); + out->Print("public $name$(Channel channel) : base(channel)\n", + "name", GetClientClassName(service)); out->Print("{\n"); out->Print("}\n"); + out->Print("public $name$(CallInvoker callInvoker) : base(callInvoker)\n", + "name", GetClientClassName(service)); + out->Print("{\n"); + out->Print("}\n\n"); for (int i = 0; i < service->method_count(); i++) { const MethodDescriptor *method = service->method(i); @@ -452,16 +370,26 @@ void GenerateClientStub(Printer* out, const ServiceDescriptor *service) { if (method_type == METHODTYPE_NO_STREAMING) { // unary calls have an extra synchronous stub method - out->Print( - "public override $response$ $methodname$($request$ request, CallOptions options)\n", - "methodname", method->name(), "request", - GetClassName(method->input_type()), "response", - GetClassName(method->output_type())); + out->Print("public virtual $response$ $methodname$($request$ request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken))\n", + "methodname", method->name(), "request", + GetClassName(method->input_type()), "response", + GetClassName(method->output_type())); + out->Print("{\n"); + out->Indent(); + out->Print("return $methodname$(request, new CallOptions(headers, deadline, cancellationToken));\n", + "methodname", method->name()); + out->Outdent(); + out->Print("}\n"); + + // overload taking CallOptions as a param + out->Print("public virtual $response$ $methodname$($request$ request, CallOptions options)\n", + "methodname", method->name(), "request", + GetClassName(method->input_type()), "response", + GetClassName(method->output_type())); out->Print("{\n"); out->Indent(); - out->Print("var call = CreateCall($methodfield$, options);\n", + out->Print("return CallInvoker.BlockingUnaryCall($methodfield$, options, request);\n", "methodfield", GetMethodFieldName(method)); - out->Print("return Calls.BlockingUnaryCall(call, request);\n"); out->Outdent(); out->Print("}\n"); } @@ -471,27 +399,44 @@ void GenerateClientStub(Printer* out, const ServiceDescriptor *service) { method_name += "Async"; // prevent name clash with synchronous method. } out->Print( - "public override $returntype$ $methodname$($request_maybe$CallOptions options)\n", + "public virtual $returntype$ $methodname$($request_maybe$Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken))\n", + "methodname", method_name, "request_maybe", + GetMethodRequestParamMaybe(method), "returntype", + GetMethodReturnTypeClient(method)); + out->Print("{\n"); + out->Indent(); + + out->Print("return $methodname$($request_maybe$new CallOptions(headers, deadline, cancellationToken));\n", + "methodname", method_name, + "request_maybe", GetMethodRequestParamMaybe(method, true)); + out->Outdent(); + out->Print("}\n"); + + // overload taking CallOptions as a param + out->Print( + "public virtual $returntype$ $methodname$($request_maybe$CallOptions options)\n", "methodname", method_name, "request_maybe", GetMethodRequestParamMaybe(method), "returntype", GetMethodReturnTypeClient(method)); out->Print("{\n"); out->Indent(); - out->Print("var call = CreateCall($methodfield$, options);\n", - "methodfield", GetMethodFieldName(method)); switch (GetMethodType(method)) { case METHODTYPE_NO_STREAMING: - out->Print("return Calls.AsyncUnaryCall(call, request);\n"); + out->Print("return CallInvoker.AsyncUnaryCall($methodfield$, options, request);\n", + "methodfield", GetMethodFieldName(method)); break; case METHODTYPE_CLIENT_STREAMING: - out->Print("return Calls.AsyncClientStreamingCall(call);\n"); + out->Print("return CallInvoker.AsyncClientStreamingCall($methodfield$, options);\n", + "methodfield", GetMethodFieldName(method)); break; case METHODTYPE_SERVER_STREAMING: out->Print( - "return Calls.AsyncServerStreamingCall(call, request);\n"); + "return CallInvoker.AsyncServerStreamingCall($methodfield$, options, request);\n", + "methodfield", GetMethodFieldName(method)); break; case METHODTYPE_BIDI_STREAMING: - out->Print("return Calls.AsyncDuplexStreamingCall(call);\n"); + out->Print("return CallInvoker.AsyncDuplexStreamingCall($methodfield$, options);\n", + "methodfield", GetMethodFieldName(method)); break; default: GOOGLE_LOG(FATAL)<< "Can't get here."; @@ -499,6 +444,17 @@ void GenerateClientStub(Printer* out, const ServiceDescriptor *service) { out->Outdent(); out->Print("}\n"); } + + // override NewInstance method + out->Print("protected override $name$ NewInstance(CallInvoker callInvoker)\n", + "name", GetClientClassName(service)); + out->Print("{\n"); + out->Indent(); + out->Print("return new $name$(callInvoker);\n", + "name", GetClientClassName(service)); + out->Outdent(); + out->Print("}\n"); + out->Outdent(); out->Print("}\n"); out->Print("\n"); @@ -567,7 +523,7 @@ void GenerateService(Printer* out, const ServiceDescriptor *service) { } GenerateServiceDescriptorProperty(out, service); GenerateClientInterface(out, service); - GenerateClientBaseClass(out, service); + //GenerateClientBaseClass(out, service); GenerateServerInterface(out, service); GenerateServerClass(out, service); GenerateClientStub(out, service);