Merge pull request #2459 from jtattermusch/csharp_metadata_refactoring

C# client-side metadata refactoring
pull/2476/head
Stanley Cheung 10 years ago
commit 4ff154ef30
  1. 50
      src/compiler/csharp_generator.cc
  2. 8
      src/csharp/Grpc.Auth/OAuth2InterceptorFactory.cs
  3. 10
      src/csharp/Grpc.Core.Tests/Internal/MetadataArraySafeHandleTest.cs
  4. 2
      src/csharp/Grpc.Core/Calls.cs
  5. 41
      src/csharp/Grpc.Core/ClientBase.cs
  6. 3
      src/csharp/Grpc.Core/Grpc.Core.csproj
  7. 8
      src/csharp/Grpc.Core/Internal/MetadataArraySafeHandle.cs
  8. 177
      src/csharp/Grpc.Core/Metadata.cs
  9. 64
      src/csharp/Grpc.Core/Stub/StubConfiguration.cs
  10. 1
      src/csharp/Grpc.Core/Version.cs
  11. 14
      src/csharp/Grpc.Examples.MathClient/MathClient.cs
  12. 10
      src/csharp/Grpc.Examples.Tests/MathClientServerTests.cs
  13. 26
      src/csharp/Grpc.Examples/MathExamples.cs
  14. 58
      src/csharp/Grpc.Examples/MathGrpc.cs
  15. 2
      src/csharp/Grpc.HealthCheck.Tests/HealthClientServerTest.cs
  16. 34
      src/csharp/Grpc.HealthCheck/HealthGrpc.cs
  17. 9
      src/csharp/Grpc.IntegrationTesting/InteropClient.cs
  18. 2
      src/csharp/Grpc.IntegrationTesting/InteropClientServerTest.cs
  19. 82
      src/csharp/Grpc.IntegrationTesting/TestGrpc.cs
  20. 9
      src/csharp/generate_proto_csharp.sh

@ -257,7 +257,7 @@ void GenerateStaticMethodField(Printer* out, const MethodDescriptor *method) {
} }
void GenerateClientInterface(Printer* out, const ServiceDescriptor *service) { void GenerateClientInterface(Printer* out, const ServiceDescriptor *service) {
out->Print("// client-side stub interface\n"); out->Print("// client interface\n");
out->Print("public interface $name$\n", "name", out->Print("public interface $name$\n", "name",
GetClientInterfaceName(service)); GetClientInterfaceName(service));
out->Print("{\n"); out->Print("{\n");
@ -269,7 +269,7 @@ void GenerateClientInterface(Printer* out, const ServiceDescriptor *service) {
if (method_type == METHODTYPE_NO_STREAMING) { if (method_type == METHODTYPE_NO_STREAMING) {
// unary calls have an extra synchronous stub method // unary calls have an extra synchronous stub method
out->Print( out->Print(
"$response$ $methodname$($request$ request, CancellationToken token = default(CancellationToken));\n", "$response$ $methodname$($request$ request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));\n",
"methodname", method->name(), "request", "methodname", method->name(), "request",
GetClassName(method->input_type()), "response", GetClassName(method->input_type()), "response",
GetClassName(method->output_type())); GetClassName(method->output_type()));
@ -280,7 +280,7 @@ void GenerateClientInterface(Printer* out, const ServiceDescriptor *service) {
method_name += "Async"; // prevent name clash with synchronous method. method_name += "Async"; // prevent name clash with synchronous method.
} }
out->Print( out->Print(
"$returntype$ $methodname$($request_maybe$CancellationToken token = default(CancellationToken));\n", "$returntype$ $methodname$($request_maybe$Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));\n",
"methodname", method_name, "request_maybe", "methodname", method_name, "request_maybe",
GetMethodRequestParamMaybe(method), "returntype", GetMethodRequestParamMaybe(method), "returntype",
GetMethodReturnTypeClient(method)); GetMethodReturnTypeClient(method));
@ -312,7 +312,7 @@ void GenerateServerInterface(Printer* out, const ServiceDescriptor *service) {
void GenerateClientStub(Printer* out, const ServiceDescriptor *service) { void GenerateClientStub(Printer* out, const ServiceDescriptor *service) {
out->Print("// client stub\n"); out->Print("// client stub\n");
out->Print( out->Print(
"public class $name$ : AbstractStub<$name$, StubConfiguration>, $interface$\n", "public class $name$ : ClientBase, $interface$\n",
"name", GetClientClassName(service), "interface", "name", GetClientClassName(service), "interface",
GetClientInterfaceName(service)); GetClientInterfaceName(service));
out->Print("{\n"); out->Print("{\n");
@ -320,12 +320,7 @@ void GenerateClientStub(Printer* out, const ServiceDescriptor *service) {
// constructors // constructors
out->Print( out->Print(
"public $name$(Channel channel) : this(channel, StubConfiguration.Default)\n", "public $name$(Channel channel) : base(channel)\n",
"name", GetClientClassName(service));
out->Print("{\n");
out->Print("}\n");
out->Print(
"public $name$(Channel channel, StubConfiguration config) : base(channel, config)\n",
"name", GetClientClassName(service)); "name", GetClientClassName(service));
out->Print("{\n"); out->Print("{\n");
out->Print("}\n"); out->Print("}\n");
@ -337,16 +332,16 @@ void GenerateClientStub(Printer* out, const ServiceDescriptor *service) {
if (method_type == METHODTYPE_NO_STREAMING) { if (method_type == METHODTYPE_NO_STREAMING) {
// unary calls have an extra synchronous stub method // unary calls have an extra synchronous stub method
out->Print( out->Print(
"public $response$ $methodname$($request$ request, CancellationToken token = default(CancellationToken))\n", "public $response$ $methodname$($request$ request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))\n",
"methodname", method->name(), "request", "methodname", method->name(), "request",
GetClassName(method->input_type()), "response", GetClassName(method->input_type()), "response",
GetClassName(method->output_type())); GetClassName(method->output_type()));
out->Print("{\n"); out->Print("{\n");
out->Indent(); out->Indent();
out->Print("var call = CreateCall($servicenamefield$, $methodfield$);\n", out->Print("var call = CreateCall($servicenamefield$, $methodfield$, headers);\n",
"servicenamefield", GetServiceNameFieldName(), "methodfield", "servicenamefield", GetServiceNameFieldName(), "methodfield",
GetMethodFieldName(method)); GetMethodFieldName(method));
out->Print("return Calls.BlockingUnaryCall(call, request, token);\n"); out->Print("return Calls.BlockingUnaryCall(call, request, cancellationToken);\n");
out->Outdent(); out->Outdent();
out->Print("}\n"); out->Print("}\n");
} }
@ -356,28 +351,28 @@ void GenerateClientStub(Printer* out, const ServiceDescriptor *service) {
method_name += "Async"; // prevent name clash with synchronous method. method_name += "Async"; // prevent name clash with synchronous method.
} }
out->Print( out->Print(
"public $returntype$ $methodname$($request_maybe$CancellationToken token = default(CancellationToken))\n", "public $returntype$ $methodname$($request_maybe$Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))\n",
"methodname", method_name, "request_maybe", "methodname", method_name, "request_maybe",
GetMethodRequestParamMaybe(method), "returntype", GetMethodRequestParamMaybe(method), "returntype",
GetMethodReturnTypeClient(method)); GetMethodReturnTypeClient(method));
out->Print("{\n"); out->Print("{\n");
out->Indent(); out->Indent();
out->Print("var call = CreateCall($servicenamefield$, $methodfield$);\n", out->Print("var call = CreateCall($servicenamefield$, $methodfield$, headers);\n",
"servicenamefield", GetServiceNameFieldName(), "methodfield", "servicenamefield", GetServiceNameFieldName(), "methodfield",
GetMethodFieldName(method)); GetMethodFieldName(method));
switch (GetMethodType(method)) { switch (GetMethodType(method)) {
case METHODTYPE_NO_STREAMING: case METHODTYPE_NO_STREAMING:
out->Print("return Calls.AsyncUnaryCall(call, request, token);\n"); out->Print("return Calls.AsyncUnaryCall(call, request, cancellationToken);\n");
break; break;
case METHODTYPE_CLIENT_STREAMING: case METHODTYPE_CLIENT_STREAMING:
out->Print("return Calls.AsyncClientStreamingCall(call, token);\n"); out->Print("return Calls.AsyncClientStreamingCall(call, cancellationToken);\n");
break; break;
case METHODTYPE_SERVER_STREAMING: case METHODTYPE_SERVER_STREAMING:
out->Print( out->Print(
"return Calls.AsyncServerStreamingCall(call, request, token);\n"); "return Calls.AsyncServerStreamingCall(call, request, cancellationToken);\n");
break; break;
case METHODTYPE_BIDI_STREAMING: case METHODTYPE_BIDI_STREAMING:
out->Print("return Calls.AsyncDuplexStreamingCall(call, token);\n"); out->Print("return Calls.AsyncDuplexStreamingCall(call, cancellationToken);\n");
break; break;
default: default:
GOOGLE_LOG(FATAL)<< "Can't get here."; GOOGLE_LOG(FATAL)<< "Can't get here.";
@ -423,9 +418,9 @@ void GenerateBindServiceMethod(Printer* out, const ServiceDescriptor *service) {
} }
void GenerateNewStubMethods(Printer* out, const ServiceDescriptor *service) { void GenerateNewStubMethods(Printer* out, const ServiceDescriptor *service) {
out->Print("// creates a new client stub\n"); out->Print("// creates a new client\n");
out->Print("public static $interface$ NewStub(Channel channel)\n", out->Print("public static $classname$ NewClient(Channel channel)\n",
"interface", GetClientInterfaceName(service)); "classname", GetClientClassName(service));
out->Print("{\n"); out->Print("{\n");
out->Indent(); out->Indent();
out->Print("return new $classname$(channel);\n", "classname", out->Print("return new $classname$(channel);\n", "classname",
@ -433,17 +428,6 @@ void GenerateNewStubMethods(Printer* out, const ServiceDescriptor *service) {
out->Outdent(); out->Outdent();
out->Print("}\n"); out->Print("}\n");
out->Print("\n"); out->Print("\n");
out->Print("// creates a new client stub\n");
out->Print(
"public static $interface$ NewStub(Channel channel, StubConfiguration config)\n",
"interface", GetClientInterfaceName(service));
out->Print("{\n");
out->Indent();
out->Print("return new $classname$(channel, config);\n", "classname",
GetClientClassName(service));
out->Outdent();
out->Print("}\n");
} }
void GenerateService(Printer* out, const ServiceDescriptor *service) { void GenerateService(Printer* out, const ServiceDescriptor *service) {

@ -52,10 +52,10 @@ namespace Grpc.Auth
/// <summary> /// <summary>
/// Creates OAuth2 interceptor. /// Creates OAuth2 interceptor.
/// </summary> /// </summary>
public static HeaderInterceptorDelegate Create(GoogleCredential googleCredential) public static MetadataInterceptorDelegate Create(GoogleCredential googleCredential)
{ {
var interceptor = new OAuth2Interceptor(googleCredential.InternalCredential, SystemClock.Default); var interceptor = new OAuth2Interceptor(googleCredential.InternalCredential, SystemClock.Default);
return new HeaderInterceptorDelegate(interceptor.InterceptHeaders); return new MetadataInterceptorDelegate(interceptor.InterceptHeaders);
} }
/// <summary> /// <summary>
@ -94,10 +94,10 @@ namespace Grpc.Auth
return credential.Token.AccessToken; return credential.Token.AccessToken;
} }
public void InterceptHeaders(Metadata.Builder headerBuilder) public void InterceptHeaders(Metadata metadata)
{ {
var accessToken = GetAccessToken(CancellationToken.None); var accessToken = GetAccessToken(CancellationToken.None);
headerBuilder.Add(new Metadata.MetadataEntry(AuthorizationHeader, Schema + " " + accessToken)); metadata.Add(new Metadata.Entry(AuthorizationHeader, Schema + " " + accessToken));
} }
} }
} }

@ -44,17 +44,17 @@ namespace Grpc.Core.Internal.Tests
[Test] [Test]
public void CreateEmptyAndDestroy() public void CreateEmptyAndDestroy()
{ {
var metadata = Metadata.CreateBuilder().Build(); var nativeMetadata = MetadataArraySafeHandle.Create(new Metadata());
var nativeMetadata = MetadataArraySafeHandle.Create(metadata);
nativeMetadata.Dispose(); nativeMetadata.Dispose();
} }
[Test] [Test]
public void CreateAndDestroy() public void CreateAndDestroy()
{ {
var metadata = Metadata.CreateBuilder() var metadata = new Metadata {
.Add(new Metadata.MetadataEntry("host", "somehost")) new Metadata.Entry("host", "somehost"),
.Add(new Metadata.MetadataEntry("header2", "header value")).Build(); new Metadata.Entry("header2", "header value"),
};
var nativeMetadata = MetadataArraySafeHandle.Create(metadata); var nativeMetadata = MetadataArraySafeHandle.Create(metadata);
nativeMetadata.Dispose(); nativeMetadata.Dispose();
} }

@ -39,7 +39,7 @@ using Grpc.Core.Internal;
namespace Grpc.Core namespace Grpc.Core
{ {
/// <summary> /// <summary>
/// Helper methods for generated client stubs to make RPC calls. /// Helper methods for generated clients to make RPC calls.
/// </summary> /// </summary>
public static class Calls public static class Calls
{ {

@ -32,26 +32,39 @@
#endregion #endregion
using System; using System;
using System.Collections.Generic;
using Grpc.Core.Internal; using Grpc.Core.Internal;
namespace Grpc.Core namespace Grpc.Core
{ {
// TODO: support adding timeout to methods. public delegate void MetadataInterceptorDelegate(Metadata metadata);
/// <summary> /// <summary>
/// Base for client-side stubs. /// Base class for client-side stubs.
/// </summary> /// </summary>
public abstract class AbstractStub<TStub, TConfig> public abstract class ClientBase
where TConfig : StubConfiguration
{ {
readonly Channel channel; readonly Channel channel;
readonly TConfig config;
public AbstractStub(Channel channel, TConfig config) public ClientBase(Channel channel)
{ {
this.channel = channel; this.channel = channel;
this.config = config;
} }
/// <summary>
/// Can be used to register a custom header (initial metadata) interceptor.
/// The delegate each time before a new call on this client is started.
/// </summary>
public MetadataInterceptorDelegate HeaderInterceptor
{
get;
set;
}
/// <summary>
/// Channel associated with this client.
/// </summary>
public Channel Channel public Channel Channel
{ {
get get
@ -63,13 +76,19 @@ namespace Grpc.Core
/// <summary> /// <summary>
/// Creates a new call to given method. /// Creates a new call to given method.
/// </summary> /// </summary>
protected Call<TRequest, TResponse> CreateCall<TRequest, TResponse>(string serviceName, Method<TRequest, TResponse> method) protected Call<TRequest, TResponse> CreateCall<TRequest, TResponse>(string serviceName, Method<TRequest, TResponse> method, Metadata metadata)
where TRequest : class where TRequest : class
where TResponse : class where TResponse : class
{ {
var headerBuilder = Metadata.CreateBuilder(); var interceptor = HeaderInterceptor;
config.HeaderInterceptor(headerBuilder); if (interceptor != null)
return new Call<TRequest, TResponse>(serviceName, method, channel, headerBuilder.Build()); {
metadata = metadata ?? new Metadata();
interceptor(metadata);
metadata.Freeze();
}
metadata = metadata ?? Metadata.Empty;
return new Call<TRequest, TResponse>(serviceName, method, channel, metadata);
} }
} }
} }

@ -88,8 +88,7 @@
<Compile Include="ServerCredentials.cs" /> <Compile Include="ServerCredentials.cs" />
<Compile Include="Metadata.cs" /> <Compile Include="Metadata.cs" />
<Compile Include="Internal\MetadataArraySafeHandle.cs" /> <Compile Include="Internal\MetadataArraySafeHandle.cs" />
<Compile Include="Stub\AbstractStub.cs" /> <Compile Include="ClientBase.cs" />
<Compile Include="Stub\StubConfiguration.cs" />
<Compile Include="Internal\ServerCalls.cs" /> <Compile Include="Internal\ServerCalls.cs" />
<Compile Include="ServerMethods.cs" /> <Compile Include="ServerMethods.cs" />
<Compile Include="Internal\ClientRequestStream.cs" /> <Compile Include="Internal\ClientRequestStream.cs" />

@ -54,11 +54,11 @@ namespace Grpc.Core.Internal
public static MetadataArraySafeHandle Create(Metadata metadata) public static MetadataArraySafeHandle Create(Metadata metadata)
{ {
var entries = metadata.Entries; // TODO(jtattermusch): we might wanna check that the metadata is readonly
var metadataArray = grpcsharp_metadata_array_create(new UIntPtr((ulong)entries.Count)); var metadataArray = grpcsharp_metadata_array_create(new UIntPtr((ulong)metadata.Count));
for (int i = 0; i < entries.Count; i++) for (int i = 0; i < metadata.Count; i++)
{ {
grpcsharp_metadata_array_add(metadataArray, entries[i].Key, entries[i].ValueBytes, new UIntPtr((ulong)entries[i].ValueBytes.Length)); grpcsharp_metadata_array_add(metadataArray, metadata[i].Key, metadata[i].ValueBytes, new UIntPtr((ulong)metadata[i].ValueBytes.Length));
} }
return metadataArray; return metadataArray;
} }

@ -30,55 +30,163 @@
#endregion #endregion
using System; using System;
using System.Collections;
using System.Collections.Generic; using System.Collections.Generic;
using System.Collections.Immutable; using System.Collections.Immutable;
using System.Collections.Specialized;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
using System.Text; using System.Text;
using Grpc.Core.Utils;
namespace Grpc.Core namespace Grpc.Core
{ {
/// <summary> /// <summary>
/// gRPC call metadata. /// Provides access to read and write metadata values to be exchanged during a call.
/// </summary> /// </summary>
public class Metadata public sealed class Metadata : IList<Metadata.Entry>
{ {
public static readonly Metadata Empty = new Metadata(ImmutableList<MetadataEntry>.Empty); /// <summary>
/// An read-only instance of metadata containing no entries.
/// </summary>
public static readonly Metadata Empty = new Metadata().Freeze();
readonly List<Entry> entries;
bool readOnly;
public Metadata()
{
this.entries = new List<Entry>();
}
public Metadata(ICollection<Entry> entries)
{
this.entries = new List<Entry>(entries);
}
/// <summary>
/// Makes this object read-only.
/// </summary>
/// <returns>this object</returns>
public Metadata Freeze()
{
this.readOnly = true;
return this;
}
// TODO: add support for access by key
#region IList members
public int IndexOf(Metadata.Entry item)
{
return entries.IndexOf(item);
}
readonly ImmutableList<MetadataEntry> entries; public void Insert(int index, Metadata.Entry item)
{
CheckWriteable();
entries.Insert(index, item);
}
public Metadata(ImmutableList<MetadataEntry> entries) public void RemoveAt(int index)
{ {
this.entries = entries; CheckWriteable();
entries.RemoveAt(index);
} }
public ImmutableList<MetadataEntry> Entries public Metadata.Entry this[int index]
{ {
get get
{ {
return this.entries; return entries[index];
}
set
{
CheckWriteable();
entries[index] = value;
} }
} }
public static Builder CreateBuilder() public void Add(Metadata.Entry item)
{
CheckWriteable();
entries.Add(item);
}
public void Clear()
{
CheckWriteable();
entries.Clear();
}
public bool Contains(Metadata.Entry item)
{
return entries.Contains(item);
}
public void CopyTo(Metadata.Entry[] array, int arrayIndex)
{ {
return new Builder(); entries.CopyTo(array, arrayIndex);
} }
public struct MetadataEntry public int Count
{
get { return entries.Count; }
}
public bool IsReadOnly
{
get { return readOnly; }
}
public bool Remove(Metadata.Entry item)
{
CheckWriteable();
return entries.Remove(item);
}
public IEnumerator<Metadata.Entry> GetEnumerator()
{
return entries.GetEnumerator();
}
IEnumerator System.Collections.IEnumerable.GetEnumerator()
{
return entries.GetEnumerator();
}
private void CheckWriteable()
{
Preconditions.CheckState(!readOnly, "Object is read only");
}
#endregion
/// <summary>
/// Metadata entry
/// </summary>
public struct Entry
{ {
private static readonly Encoding Encoding = Encoding.ASCII;
readonly string key; readonly string key;
readonly byte[] valueBytes; string value;
byte[] valueBytes;
public MetadataEntry(string key, byte[] valueBytes) public Entry(string key, byte[] valueBytes)
{ {
this.key = key; this.key = Preconditions.CheckNotNull(key);
this.valueBytes = valueBytes; this.value = null;
this.valueBytes = Preconditions.CheckNotNull(valueBytes);
} }
public MetadataEntry(string key, string value) public Entry(string key, string value)
{ {
this.key = key; this.key = Preconditions.CheckNotNull(key);
this.valueBytes = Encoding.ASCII.GetBytes(value); this.value = Preconditions.CheckNotNull(value);
this.valueBytes = null;
} }
public string Key public string Key
@ -89,38 +197,29 @@ namespace Grpc.Core
} }
} }
// TODO: using ByteString would guarantee immutability.
public byte[] ValueBytes public byte[] ValueBytes
{ {
get get
{ {
return this.valueBytes; if (valueBytes == null)
{
valueBytes = Encoding.GetBytes(value);
}
return valueBytes;
} }
} }
}
public class Builder public string Value
{
readonly List<Metadata.MetadataEntry> entries = new List<Metadata.MetadataEntry>();
public List<MetadataEntry> Entries
{ {
get get
{ {
return entries; if (value == null)
{
value = Encoding.GetString(valueBytes);
}
return value;
} }
} }
public Builder Add(MetadataEntry entry)
{
entries.Add(entry);
return this;
}
public Metadata Build()
{
return new Metadata(entries.ToImmutableList());
}
} }
} }
} }

@ -1,64 +0,0 @@
#region Copyright notice and license
// Copyright 2015, Google Inc.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#endregion
using System;
using Grpc.Core.Internal;
using Grpc.Core.Utils;
namespace Grpc.Core
{
public delegate void HeaderInterceptorDelegate(Metadata.Builder headerBuilder);
public class StubConfiguration
{
/// <summary>
/// The default stub configuration.
/// </summary>
public static readonly StubConfiguration Default = new StubConfiguration((headerBuilder) => { });
readonly HeaderInterceptorDelegate headerInterceptor;
public StubConfiguration(HeaderInterceptorDelegate headerInterceptor)
{
this.headerInterceptor = Preconditions.CheckNotNull(headerInterceptor);
}
public HeaderInterceptorDelegate HeaderInterceptor
{
get
{
return headerInterceptor;
}
}
}
}

@ -3,4 +3,3 @@ using System.Runtime.CompilerServices;
// The current version of gRPC C#. // The current version of gRPC C#.
[assembly: AssemblyVersion("0.6.0.*")] [assembly: AssemblyVersion("0.6.0.*")]

@ -41,18 +41,18 @@ namespace math
{ {
using (Channel channel = new Channel("127.0.0.1", 23456)) using (Channel channel = new Channel("127.0.0.1", 23456))
{ {
Math.IMathClient stub = new Math.MathClient(channel); Math.IMathClient client = new Math.MathClient(channel);
MathExamples.DivExample(stub); MathExamples.DivExample(client);
MathExamples.DivAsyncExample(stub).Wait(); MathExamples.DivAsyncExample(client).Wait();
MathExamples.FibExample(stub).Wait(); MathExamples.FibExample(client).Wait();
MathExamples.SumExample(stub).Wait(); MathExamples.SumExample(client).Wait();
MathExamples.DivManyExample(stub).Wait(); MathExamples.DivManyExample(client).Wait();
MathExamples.DependendRequestsExample(stub).Wait(); MathExamples.DependendRequestsExample(client).Wait();
} }
GrpcEnvironment.Shutdown(); GrpcEnvironment.Shutdown();

@ -49,7 +49,7 @@ namespace math.Tests
string host = "localhost"; string host = "localhost";
Server server; Server server;
Channel channel; Channel channel;
Math.IMathClient client; Math.MathClient client;
[TestFixtureSetUp] [TestFixtureSetUp]
public void Init() public void Init()
@ -59,14 +59,14 @@ namespace math.Tests
int port = server.AddListeningPort(host, Server.PickUnusedPort); int port = server.AddListeningPort(host, Server.PickUnusedPort);
server.Start(); server.Start();
channel = new Channel(host, port); channel = new Channel(host, port);
client = Math.NewClient(channel);
// TODO(jtattermusch): get rid of the custom header here once we have dedicated tests // TODO(jtattermusch): get rid of the custom header here once we have dedicated tests
// for header support. // for header support.
var stubConfig = new StubConfiguration((headerBuilder) => client.HeaderInterceptor = (metadata) =>
{ {
headerBuilder.Add(new Metadata.MetadataEntry("customHeader", "abcdef")); metadata.Add(new Metadata.Entry("customHeader", "abcdef"));
}); };
client = Math.NewStub(channel, stubConfig);
} }
[TestFixtureTearDown] [TestFixtureTearDown]

@ -38,29 +38,29 @@ namespace math
{ {
public static class MathExamples public static class MathExamples
{ {
public static void DivExample(Math.IMathClient stub) public static void DivExample(Math.IMathClient client)
{ {
DivReply result = stub.Div(new DivArgs.Builder { Dividend = 10, Divisor = 3 }.Build()); DivReply result = client.Div(new DivArgs.Builder { Dividend = 10, Divisor = 3 }.Build());
Console.WriteLine("Div Result: " + result); Console.WriteLine("Div Result: " + result);
} }
public static async Task DivAsyncExample(Math.IMathClient stub) public static async Task DivAsyncExample(Math.IMathClient client)
{ {
Task<DivReply> resultTask = stub.DivAsync(new DivArgs.Builder { Dividend = 4, Divisor = 5 }.Build()); Task<DivReply> resultTask = client.DivAsync(new DivArgs.Builder { Dividend = 4, Divisor = 5 }.Build());
DivReply result = await resultTask; DivReply result = await resultTask;
Console.WriteLine("DivAsync Result: " + result); Console.WriteLine("DivAsync Result: " + result);
} }
public static async Task FibExample(Math.IMathClient stub) public static async Task FibExample(Math.IMathClient client)
{ {
using (var call = stub.Fib(new FibArgs.Builder { Limit = 5 }.Build())) using (var call = client.Fib(new FibArgs.Builder { Limit = 5 }.Build()))
{ {
List<Num> result = await call.ResponseStream.ToList(); List<Num> result = await call.ResponseStream.ToList();
Console.WriteLine("Fib Result: " + string.Join("|", result)); Console.WriteLine("Fib Result: " + string.Join("|", result));
} }
} }
public static async Task SumExample(Math.IMathClient stub) public static async Task SumExample(Math.IMathClient client)
{ {
var numbers = new List<Num> var numbers = new List<Num>
{ {
@ -69,14 +69,14 @@ namespace math
new Num.Builder { Num_ = 3 }.Build() new Num.Builder { Num_ = 3 }.Build()
}; };
using (var call = stub.Sum()) using (var call = client.Sum())
{ {
await call.RequestStream.WriteAll(numbers); await call.RequestStream.WriteAll(numbers);
Console.WriteLine("Sum Result: " + await call.Result); Console.WriteLine("Sum Result: " + await call.Result);
} }
} }
public static async Task DivManyExample(Math.IMathClient stub) public static async Task DivManyExample(Math.IMathClient client)
{ {
var divArgsList = new List<DivArgs> var divArgsList = new List<DivArgs>
{ {
@ -84,14 +84,14 @@ namespace math
new DivArgs.Builder { Dividend = 100, Divisor = 21 }.Build(), new DivArgs.Builder { Dividend = 100, Divisor = 21 }.Build(),
new DivArgs.Builder { Dividend = 7, Divisor = 2 }.Build() new DivArgs.Builder { Dividend = 7, Divisor = 2 }.Build()
}; };
using (var call = stub.DivMany()) using (var call = client.DivMany())
{ {
await call.RequestStream.WriteAll(divArgsList); await call.RequestStream.WriteAll(divArgsList);
Console.WriteLine("DivMany Result: " + string.Join("|", await call.ResponseStream.ToList())); Console.WriteLine("DivMany Result: " + string.Join("|", await call.ResponseStream.ToList()));
} }
} }
public static async Task DependendRequestsExample(Math.IMathClient stub) public static async Task DependendRequestsExample(Math.IMathClient client)
{ {
var numbers = new List<Num> var numbers = new List<Num>
{ {
@ -101,13 +101,13 @@ namespace math
}; };
Num sum; Num sum;
using (var sumCall = stub.Sum()) using (var sumCall = client.Sum())
{ {
await sumCall.RequestStream.WriteAll(numbers); await sumCall.RequestStream.WriteAll(numbers);
sum = await sumCall.Result; sum = await sumCall.Result;
} }
DivReply result = await stub.DivAsync(new DivArgs.Builder { Dividend = sum.Num_, Divisor = numbers.Count }.Build()); DivReply result = await client.DivAsync(new DivArgs.Builder { Dividend = sum.Num_, Divisor = numbers.Count }.Build());
Console.WriteLine("Avg Result: " + result); Console.WriteLine("Avg Result: " + result);
} }
} }

@ -41,14 +41,14 @@ namespace math {
__Marshaller_Num, __Marshaller_Num,
__Marshaller_Num); __Marshaller_Num);
// client-side stub interface // client interface
public interface IMathClient public interface IMathClient
{ {
global::math.DivReply Div(global::math.DivArgs request, CancellationToken token = default(CancellationToken)); global::math.DivReply Div(global::math.DivArgs request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
Task<global::math.DivReply> DivAsync(global::math.DivArgs request, CancellationToken token = default(CancellationToken)); Task<global::math.DivReply> DivAsync(global::math.DivArgs request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
AsyncDuplexStreamingCall<global::math.DivArgs, global::math.DivReply> DivMany(CancellationToken token = default(CancellationToken)); AsyncDuplexStreamingCall<global::math.DivArgs, global::math.DivReply> DivMany(Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
AsyncServerStreamingCall<global::math.Num> Fib(global::math.FibArgs request, CancellationToken token = default(CancellationToken)); AsyncServerStreamingCall<global::math.Num> Fib(global::math.FibArgs request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
AsyncClientStreamingCall<global::math.Num, global::math.Num> Sum(CancellationToken token = default(CancellationToken)); AsyncClientStreamingCall<global::math.Num, global::math.Num> Sum(Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
} }
// server-side interface // server-side interface
@ -61,38 +61,35 @@ namespace math {
} }
// client stub // client stub
public class MathClient : AbstractStub<MathClient, StubConfiguration>, IMathClient public class MathClient : ClientBase, IMathClient
{ {
public MathClient(Channel channel) : this(channel, StubConfiguration.Default) public MathClient(Channel channel) : base(channel)
{ {
} }
public MathClient(Channel channel, StubConfiguration config) : base(channel, config) public global::math.DivReply Div(global::math.DivArgs request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_Div, headers);
return Calls.BlockingUnaryCall(call, request, cancellationToken);
} }
public global::math.DivReply Div(global::math.DivArgs request, CancellationToken token = default(CancellationToken)) public Task<global::math.DivReply> DivAsync(global::math.DivArgs request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_Div); var call = CreateCall(__ServiceName, __Method_Div, headers);
return Calls.BlockingUnaryCall(call, request, token); return Calls.AsyncUnaryCall(call, request, cancellationToken);
} }
public Task<global::math.DivReply> DivAsync(global::math.DivArgs request, CancellationToken token = default(CancellationToken)) public AsyncDuplexStreamingCall<global::math.DivArgs, global::math.DivReply> DivMany(Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_Div); var call = CreateCall(__ServiceName, __Method_DivMany, headers);
return Calls.AsyncUnaryCall(call, request, token); return Calls.AsyncDuplexStreamingCall(call, cancellationToken);
} }
public AsyncDuplexStreamingCall<global::math.DivArgs, global::math.DivReply> DivMany(CancellationToken token = default(CancellationToken)) public AsyncServerStreamingCall<global::math.Num> Fib(global::math.FibArgs request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_DivMany); var call = CreateCall(__ServiceName, __Method_Fib, headers);
return Calls.AsyncDuplexStreamingCall(call, token); return Calls.AsyncServerStreamingCall(call, request, cancellationToken);
} }
public AsyncServerStreamingCall<global::math.Num> Fib(global::math.FibArgs request, CancellationToken token = default(CancellationToken)) public AsyncClientStreamingCall<global::math.Num, global::math.Num> Sum(Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_Fib); var call = CreateCall(__ServiceName, __Method_Sum, headers);
return Calls.AsyncServerStreamingCall(call, request, token); return Calls.AsyncClientStreamingCall(call, cancellationToken);
}
public AsyncClientStreamingCall<global::math.Num, global::math.Num> Sum(CancellationToken token = default(CancellationToken))
{
var call = CreateCall(__ServiceName, __Method_Sum);
return Calls.AsyncClientStreamingCall(call, token);
} }
} }
@ -106,17 +103,12 @@ namespace math {
.AddMethod(__Method_Sum, serviceImpl.Sum).Build(); .AddMethod(__Method_Sum, serviceImpl.Sum).Build();
} }
// creates a new client stub // creates a new client
public static IMathClient NewStub(Channel channel) public static MathClient NewClient(Channel channel)
{ {
return new MathClient(channel); return new MathClient(channel);
} }
// creates a new client stub
public static IMathClient NewStub(Channel channel, StubConfiguration config)
{
return new MathClient(channel, config);
}
} }
} }
#endregion #endregion

@ -63,7 +63,7 @@ namespace Grpc.HealthCheck.Tests
server.Start(); server.Start();
channel = new Channel(Host, port); channel = new Channel(Host, port);
client = Grpc.Health.V1Alpha.Health.NewStub(channel); client = Grpc.Health.V1Alpha.Health.NewClient(channel);
} }
[TestFixtureTearDown] [TestFixtureTearDown]

@ -21,11 +21,11 @@ namespace Grpc.Health.V1Alpha {
__Marshaller_HealthCheckRequest, __Marshaller_HealthCheckRequest,
__Marshaller_HealthCheckResponse); __Marshaller_HealthCheckResponse);
// client-side stub interface // client interface
public interface IHealthClient public interface IHealthClient
{ {
global::Grpc.Health.V1Alpha.HealthCheckResponse Check(global::Grpc.Health.V1Alpha.HealthCheckRequest request, CancellationToken token = default(CancellationToken)); global::Grpc.Health.V1Alpha.HealthCheckResponse Check(global::Grpc.Health.V1Alpha.HealthCheckRequest request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
Task<global::Grpc.Health.V1Alpha.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1Alpha.HealthCheckRequest request, CancellationToken token = default(CancellationToken)); Task<global::Grpc.Health.V1Alpha.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1Alpha.HealthCheckRequest request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
} }
// server-side interface // server-side interface
@ -35,23 +35,20 @@ namespace Grpc.Health.V1Alpha {
} }
// client stub // client stub
public class HealthClient : AbstractStub<HealthClient, StubConfiguration>, IHealthClient public class HealthClient : ClientBase, IHealthClient
{ {
public HealthClient(Channel channel) : this(channel, StubConfiguration.Default) public HealthClient(Channel channel) : base(channel)
{ {
} }
public HealthClient(Channel channel, StubConfiguration config) : base(channel, config) public global::Grpc.Health.V1Alpha.HealthCheckResponse Check(global::Grpc.Health.V1Alpha.HealthCheckRequest request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_Check, headers);
return Calls.BlockingUnaryCall(call, request, cancellationToken);
} }
public global::Grpc.Health.V1Alpha.HealthCheckResponse Check(global::Grpc.Health.V1Alpha.HealthCheckRequest request, CancellationToken token = default(CancellationToken)) public Task<global::Grpc.Health.V1Alpha.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1Alpha.HealthCheckRequest request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_Check); var call = CreateCall(__ServiceName, __Method_Check, headers);
return Calls.BlockingUnaryCall(call, request, token); return Calls.AsyncUnaryCall(call, request, cancellationToken);
}
public Task<global::Grpc.Health.V1Alpha.HealthCheckResponse> CheckAsync(global::Grpc.Health.V1Alpha.HealthCheckRequest request, CancellationToken token = default(CancellationToken))
{
var call = CreateCall(__ServiceName, __Method_Check);
return Calls.AsyncUnaryCall(call, request, token);
} }
} }
@ -62,17 +59,12 @@ namespace Grpc.Health.V1Alpha {
.AddMethod(__Method_Check, serviceImpl.Check).Build(); .AddMethod(__Method_Check, serviceImpl.Check).Build();
} }
// creates a new client stub // creates a new client
public static IHealthClient NewStub(Channel channel) public static HealthClient NewClient(Channel channel)
{ {
return new HealthClient(channel); return new HealthClient(channel);
} }
// creates a new client stub
public static IHealthClient NewStub(Channel channel, StubConfiguration config)
{
return new HealthClient(channel, config);
}
} }
} }
#endregion #endregion

@ -119,7 +119,7 @@ namespace Grpc.IntegrationTesting
using (Channel channel = new Channel(options.serverHost, options.serverPort.Value, credentials, channelOptions)) using (Channel channel = new Channel(options.serverHost, options.serverPort.Value, credentials, channelOptions))
{ {
var stubConfig = StubConfiguration.Default; TestService.TestServiceClient client = new TestService.TestServiceClient(channel);
if (options.testCase == "service_account_creds" || options.testCase == "compute_engine_creds") if (options.testCase == "service_account_creds" || options.testCase == "compute_engine_creds")
{ {
var credential = GoogleCredential.GetApplicationDefault(); var credential = GoogleCredential.GetApplicationDefault();
@ -127,10 +127,9 @@ namespace Grpc.IntegrationTesting
{ {
credential = credential.CreateScoped(new[] { AuthScope }); credential = credential.CreateScoped(new[] { AuthScope });
} }
stubConfig = new StubConfiguration(OAuth2InterceptorFactory.Create(credential)); client.HeaderInterceptor = OAuth2InterceptorFactory.Create(credential);
} }
TestService.ITestServiceClient client = new TestService.TestServiceClient(channel, stubConfig);
RunTestCase(options.testCase, client); RunTestCase(options.testCase, client);
} }
GrpcEnvironment.Shutdown(); GrpcEnvironment.Shutdown();
@ -363,7 +362,7 @@ namespace Grpc.IntegrationTesting
Console.WriteLine("running cancel_after_begin"); Console.WriteLine("running cancel_after_begin");
var cts = new CancellationTokenSource(); var cts = new CancellationTokenSource();
using (var call = client.StreamingInputCall(cts.Token)) using (var call = client.StreamingInputCall(cancellationToken: cts.Token))
{ {
// TODO(jtattermusch): we need this to ensure call has been initiated once we cancel it. // TODO(jtattermusch): we need this to ensure call has been initiated once we cancel it.
await Task.Delay(1000); await Task.Delay(1000);
@ -390,7 +389,7 @@ namespace Grpc.IntegrationTesting
Console.WriteLine("running cancel_after_first_response"); Console.WriteLine("running cancel_after_first_response");
var cts = new CancellationTokenSource(); var cts = new CancellationTokenSource();
using (var call = client.FullDuplexCall(cts.Token)) using (var call = client.FullDuplexCall(cancellationToken: cts.Token))
{ {
await call.RequestStream.WriteAsync(StreamingOutputCallRequest.CreateBuilder() await call.RequestStream.WriteAsync(StreamingOutputCallRequest.CreateBuilder()
.SetResponseType(PayloadType.COMPRESSABLE) .SetResponseType(PayloadType.COMPRESSABLE)

@ -65,7 +65,7 @@ namespace Grpc.IntegrationTesting
new ChannelOption(ChannelOptions.SslTargetNameOverride, TestCredentials.DefaultHostOverride) new ChannelOption(ChannelOptions.SslTargetNameOverride, TestCredentials.DefaultHostOverride)
}; };
channel = new Channel(host, port, TestCredentials.CreateTestClientCredentials(true), options); channel = new Channel(host, port, TestCredentials.CreateTestClientCredentials(true), options);
client = TestService.NewStub(channel); client = TestService.NewClient(channel);
} }
[TestFixtureTearDown] [TestFixtureTearDown]

@ -56,17 +56,17 @@ namespace grpc.testing {
__Marshaller_StreamingOutputCallRequest, __Marshaller_StreamingOutputCallRequest,
__Marshaller_StreamingOutputCallResponse); __Marshaller_StreamingOutputCallResponse);
// client-side stub interface // client interface
public interface ITestServiceClient public interface ITestServiceClient
{ {
global::grpc.testing.Empty EmptyCall(global::grpc.testing.Empty request, CancellationToken token = default(CancellationToken)); global::grpc.testing.Empty EmptyCall(global::grpc.testing.Empty request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
Task<global::grpc.testing.Empty> EmptyCallAsync(global::grpc.testing.Empty request, CancellationToken token = default(CancellationToken)); Task<global::grpc.testing.Empty> EmptyCallAsync(global::grpc.testing.Empty request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
global::grpc.testing.SimpleResponse UnaryCall(global::grpc.testing.SimpleRequest request, CancellationToken token = default(CancellationToken)); global::grpc.testing.SimpleResponse UnaryCall(global::grpc.testing.SimpleRequest request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
Task<global::grpc.testing.SimpleResponse> UnaryCallAsync(global::grpc.testing.SimpleRequest request, CancellationToken token = default(CancellationToken)); Task<global::grpc.testing.SimpleResponse> UnaryCallAsync(global::grpc.testing.SimpleRequest request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
AsyncServerStreamingCall<global::grpc.testing.StreamingOutputCallResponse> StreamingOutputCall(global::grpc.testing.StreamingOutputCallRequest request, CancellationToken token = default(CancellationToken)); AsyncServerStreamingCall<global::grpc.testing.StreamingOutputCallResponse> StreamingOutputCall(global::grpc.testing.StreamingOutputCallRequest request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
AsyncClientStreamingCall<global::grpc.testing.StreamingInputCallRequest, global::grpc.testing.StreamingInputCallResponse> StreamingInputCall(CancellationToken token = default(CancellationToken)); AsyncClientStreamingCall<global::grpc.testing.StreamingInputCallRequest, global::grpc.testing.StreamingInputCallResponse> StreamingInputCall(Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
AsyncDuplexStreamingCall<global::grpc.testing.StreamingOutputCallRequest, global::grpc.testing.StreamingOutputCallResponse> FullDuplexCall(CancellationToken token = default(CancellationToken)); AsyncDuplexStreamingCall<global::grpc.testing.StreamingOutputCallRequest, global::grpc.testing.StreamingOutputCallResponse> FullDuplexCall(Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
AsyncDuplexStreamingCall<global::grpc.testing.StreamingOutputCallRequest, global::grpc.testing.StreamingOutputCallResponse> HalfDuplexCall(CancellationToken token = default(CancellationToken)); AsyncDuplexStreamingCall<global::grpc.testing.StreamingOutputCallRequest, global::grpc.testing.StreamingOutputCallResponse> HalfDuplexCall(Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken));
} }
// server-side interface // server-side interface
@ -81,53 +81,50 @@ namespace grpc.testing {
} }
// client stub // client stub
public class TestServiceClient : AbstractStub<TestServiceClient, StubConfiguration>, ITestServiceClient public class TestServiceClient : ClientBase, ITestServiceClient
{ {
public TestServiceClient(Channel channel) : this(channel, StubConfiguration.Default) public TestServiceClient(Channel channel) : base(channel)
{ {
} }
public TestServiceClient(Channel channel, StubConfiguration config) : base(channel, config) public global::grpc.testing.Empty EmptyCall(global::grpc.testing.Empty request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_EmptyCall, headers);
return Calls.BlockingUnaryCall(call, request, cancellationToken);
} }
public global::grpc.testing.Empty EmptyCall(global::grpc.testing.Empty request, CancellationToken token = default(CancellationToken)) public Task<global::grpc.testing.Empty> EmptyCallAsync(global::grpc.testing.Empty request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_EmptyCall); var call = CreateCall(__ServiceName, __Method_EmptyCall, headers);
return Calls.BlockingUnaryCall(call, request, token); return Calls.AsyncUnaryCall(call, request, cancellationToken);
} }
public Task<global::grpc.testing.Empty> EmptyCallAsync(global::grpc.testing.Empty request, CancellationToken token = default(CancellationToken)) public global::grpc.testing.SimpleResponse UnaryCall(global::grpc.testing.SimpleRequest request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_EmptyCall); var call = CreateCall(__ServiceName, __Method_UnaryCall, headers);
return Calls.AsyncUnaryCall(call, request, token); return Calls.BlockingUnaryCall(call, request, cancellationToken);
} }
public global::grpc.testing.SimpleResponse UnaryCall(global::grpc.testing.SimpleRequest request, CancellationToken token = default(CancellationToken)) public Task<global::grpc.testing.SimpleResponse> UnaryCallAsync(global::grpc.testing.SimpleRequest request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_UnaryCall); var call = CreateCall(__ServiceName, __Method_UnaryCall, headers);
return Calls.BlockingUnaryCall(call, request, token); return Calls.AsyncUnaryCall(call, request, cancellationToken);
} }
public Task<global::grpc.testing.SimpleResponse> UnaryCallAsync(global::grpc.testing.SimpleRequest request, CancellationToken token = default(CancellationToken)) public AsyncServerStreamingCall<global::grpc.testing.StreamingOutputCallResponse> StreamingOutputCall(global::grpc.testing.StreamingOutputCallRequest request, Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_UnaryCall); var call = CreateCall(__ServiceName, __Method_StreamingOutputCall, headers);
return Calls.AsyncUnaryCall(call, request, token); return Calls.AsyncServerStreamingCall(call, request, cancellationToken);
} }
public AsyncServerStreamingCall<global::grpc.testing.StreamingOutputCallResponse> StreamingOutputCall(global::grpc.testing.StreamingOutputCallRequest request, CancellationToken token = default(CancellationToken)) public AsyncClientStreamingCall<global::grpc.testing.StreamingInputCallRequest, global::grpc.testing.StreamingInputCallResponse> StreamingInputCall(Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_StreamingOutputCall); var call = CreateCall(__ServiceName, __Method_StreamingInputCall, headers);
return Calls.AsyncServerStreamingCall(call, request, token); return Calls.AsyncClientStreamingCall(call, cancellationToken);
} }
public AsyncClientStreamingCall<global::grpc.testing.StreamingInputCallRequest, global::grpc.testing.StreamingInputCallResponse> StreamingInputCall(CancellationToken token = default(CancellationToken)) public AsyncDuplexStreamingCall<global::grpc.testing.StreamingOutputCallRequest, global::grpc.testing.StreamingOutputCallResponse> FullDuplexCall(Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_StreamingInputCall); var call = CreateCall(__ServiceName, __Method_FullDuplexCall, headers);
return Calls.AsyncClientStreamingCall(call, token); return Calls.AsyncDuplexStreamingCall(call, cancellationToken);
} }
public AsyncDuplexStreamingCall<global::grpc.testing.StreamingOutputCallRequest, global::grpc.testing.StreamingOutputCallResponse> FullDuplexCall(CancellationToken token = default(CancellationToken)) public AsyncDuplexStreamingCall<global::grpc.testing.StreamingOutputCallRequest, global::grpc.testing.StreamingOutputCallResponse> HalfDuplexCall(Metadata headers = null, CancellationToken cancellationToken = default(CancellationToken))
{ {
var call = CreateCall(__ServiceName, __Method_FullDuplexCall); var call = CreateCall(__ServiceName, __Method_HalfDuplexCall, headers);
return Calls.AsyncDuplexStreamingCall(call, token); return Calls.AsyncDuplexStreamingCall(call, cancellationToken);
}
public AsyncDuplexStreamingCall<global::grpc.testing.StreamingOutputCallRequest, global::grpc.testing.StreamingOutputCallResponse> HalfDuplexCall(CancellationToken token = default(CancellationToken))
{
var call = CreateCall(__ServiceName, __Method_HalfDuplexCall);
return Calls.AsyncDuplexStreamingCall(call, token);
} }
} }
@ -143,17 +140,12 @@ namespace grpc.testing {
.AddMethod(__Method_HalfDuplexCall, serviceImpl.HalfDuplexCall).Build(); .AddMethod(__Method_HalfDuplexCall, serviceImpl.HalfDuplexCall).Build();
} }
// creates a new client stub // creates a new client
public static ITestServiceClient NewStub(Channel channel) public static TestServiceClient NewClient(Channel channel)
{ {
return new TestServiceClient(channel); return new TestServiceClient(channel);
} }
// creates a new client stub
public static ITestServiceClient NewStub(Channel channel, StubConfiguration config)
{
return new TestServiceClient(channel, config);
}
} }
} }
#endregion #endregion

@ -32,16 +32,17 @@
set +e set +e
cd $(dirname $0) cd $(dirname $0)
PROTOC=../../bins/opt/protobuf/protoc
PLUGIN=protoc-gen-grpc=../../bins/opt/grpc_csharp_plugin PLUGIN=protoc-gen-grpc=../../bins/opt/grpc_csharp_plugin
EXAMPLES_DIR=Grpc.Examples EXAMPLES_DIR=Grpc.Examples
INTEROP_DIR=Grpc.IntegrationTesting INTEROP_DIR=Grpc.IntegrationTesting
HEALTHCHECK_DIR=Grpc.HealthCheck HEALTHCHECK_DIR=Grpc.HealthCheck
protoc --plugin=$PLUGIN --grpc_out=$EXAMPLES_DIR \ $PROTOC --plugin=$PLUGIN --grpc_out=$EXAMPLES_DIR \
-I $EXAMPLES_DIR/proto $EXAMPLES_DIR/proto/math.proto -I $EXAMPLES_DIR/proto $EXAMPLES_DIR/proto/math.proto
protoc --plugin=$PLUGIN --grpc_out=$INTEROP_DIR \ $PROTOC --plugin=$PLUGIN --grpc_out=$INTEROP_DIR \
-I $INTEROP_DIR/proto $INTEROP_DIR/proto/test.proto -I $INTEROP_DIR/proto $INTEROP_DIR/proto/test.proto
protoc --plugin=$PLUGIN --grpc_out=$HEALTHCHECK_DIR \ $PROTOC --plugin=$PLUGIN --grpc_out=$HEALTHCHECK_DIR \
-I $HEALTHCHECK_DIR/proto $HEALTHCHECK_DIR/proto/health.proto -I $HEALTHCHECK_DIR/proto $HEALTHCHECK_DIR/proto/health.proto

Loading…
Cancel
Save