mirror of https://github.com/grpc/grpc.git
parent
7fc77e06ba
commit
d0c1bfa566
27 changed files with 5116 additions and 83 deletions
@ -0,0 +1,3 @@ |
||||
bin |
||||
obj |
||||
|
@ -0,0 +1,60 @@ |
||||
<?xml version="1.0" encoding="utf-8"?> |
||||
<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> |
||||
<PropertyGroup> |
||||
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration> |
||||
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform> |
||||
<ProjectGuid>{B82B7DFE-7F7B-40EF-B3D6-064FF2B01294}</ProjectGuid> |
||||
<OutputType>Exe</OutputType> |
||||
<RootNamespace>Grpc.IntegrationTesting.QpsWorker</RootNamespace> |
||||
<AssemblyName>Grpc.IntegrationTesting.QpsWorker</AssemblyName> |
||||
<TargetFrameworkVersion>v4.5</TargetFrameworkVersion> |
||||
</PropertyGroup> |
||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' "> |
||||
<DebugSymbols>true</DebugSymbols> |
||||
<DebugType>full</DebugType> |
||||
<Optimize>false</Optimize> |
||||
<OutputPath>bin\Debug</OutputPath> |
||||
<DefineConstants>DEBUG;</DefineConstants> |
||||
<ErrorReport>prompt</ErrorReport> |
||||
<WarningLevel>4</WarningLevel> |
||||
<PlatformTarget>AnyCPU</PlatformTarget> |
||||
</PropertyGroup> |
||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' "> |
||||
<DebugType>pdbonly</DebugType> |
||||
<Optimize>true</Optimize> |
||||
<OutputPath>bin\Release</OutputPath> |
||||
<ErrorReport>prompt</ErrorReport> |
||||
<WarningLevel>4</WarningLevel> |
||||
<PlatformTarget>AnyCPU</PlatformTarget> |
||||
</PropertyGroup> |
||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'ReleaseSigned|AnyCPU' "> |
||||
<DebugType>pdbonly</DebugType> |
||||
<Optimize>true</Optimize> |
||||
<OutputPath>bin\ReleaseSigned</OutputPath> |
||||
<ErrorReport>prompt</ErrorReport> |
||||
<WarningLevel>4</WarningLevel> |
||||
<SignAssembly>True</SignAssembly> |
||||
<AssemblyOriginatorKeyFile>C:\keys\Grpc.snk</AssemblyOriginatorKeyFile> |
||||
</PropertyGroup> |
||||
<ItemGroup> |
||||
<Reference Include="System" /> |
||||
</ItemGroup> |
||||
<ItemGroup> |
||||
<Compile Include="..\Grpc.Core\Version.cs"> |
||||
<Link>Version.cs</Link> |
||||
</Compile> |
||||
<Compile Include="Program.cs" /> |
||||
<Compile Include="Properties\AssemblyInfo.cs" /> |
||||
</ItemGroup> |
||||
<Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" /> |
||||
<ItemGroup> |
||||
<ProjectReference Include="..\Grpc.Core\Grpc.Core.csproj"> |
||||
<Project>{CCC4440E-49F7-4790-B0AF-FEABB0837AE7}</Project> |
||||
<Name>Grpc.Core</Name> |
||||
</ProjectReference> |
||||
<ProjectReference Include="..\Grpc.IntegrationTesting\Grpc.IntegrationTesting.csproj"> |
||||
<Project>{C61154BA-DD4A-4838-8420-0162A28925E0}</Project> |
||||
<Name>Grpc.IntegrationTesting</Name> |
||||
</ProjectReference> |
||||
</ItemGroup> |
||||
</Project> |
@ -0,0 +1,76 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.Threading; |
||||
using System.Threading.Tasks; |
||||
using Google.Protobuf; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
|
||||
namespace Grpc.Testing |
||||
{ |
||||
/// <summary> |
||||
/// Implementation of BenchmarkService server |
||||
/// </summary> |
||||
public class BenchmarkServiceImpl : BenchmarkService.IBenchmarkService |
||||
{ |
||||
private readonly int responseSize; |
||||
|
||||
public BenchmarkServiceImpl(int responseSize) |
||||
{ |
||||
this.responseSize = responseSize; |
||||
} |
||||
|
||||
public Task<SimpleResponse> UnaryCall(SimpleRequest request, ServerCallContext context) |
||||
{ |
||||
var response = new SimpleResponse { Payload = CreateZerosPayload(responseSize) }; |
||||
return Task.FromResult(response); |
||||
} |
||||
|
||||
public async Task StreamingCall(IAsyncStreamReader<SimpleRequest> requestStream, IServerStreamWriter<SimpleResponse> responseStream, ServerCallContext context) |
||||
{ |
||||
await requestStream.ForEachAsync(async request => |
||||
{ |
||||
var response = new SimpleResponse { Payload = CreateZerosPayload(responseSize) }; |
||||
await responseStream.WriteAsync(response); |
||||
}); |
||||
} |
||||
|
||||
private static Payload CreateZerosPayload(int size) |
||||
{ |
||||
return new Payload { Body = ByteString.CopyFrom(new byte[size]) }; |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,149 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.Diagnostics; |
||||
using System.IO; |
||||
using System.Linq; |
||||
using System.Text.RegularExpressions; |
||||
using System.Threading; |
||||
using System.Threading.Tasks; |
||||
using Google.Protobuf; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
using NUnit.Framework; |
||||
using Grpc.Testing; |
||||
|
||||
namespace Grpc.IntegrationTesting |
||||
{ |
||||
/// <summary> |
||||
/// Helper methods to start client runners for performance testing. |
||||
/// </summary> |
||||
public static class ClientRunners |
||||
{ |
||||
/// <summary> |
||||
/// Creates a started client runner. |
||||
/// </summary> |
||||
public static IClientRunner CreateStarted(ClientConfig config) |
||||
{ |
||||
string target = config.ServerTargets.Single(); |
||||
Grpc.Core.Utils.Preconditions.CheckArgument(config.LoadParams.LoadCase == LoadParams.LoadOneofCase.ClosedLoop); |
||||
|
||||
var credentials = config.SecurityParams != null ? TestCredentials.CreateSslCredentials() : ChannelCredentials.Insecure; |
||||
var channel = new Channel(target, credentials); |
||||
|
||||
switch (config.RpcType) |
||||
{ |
||||
case RpcType.UNARY: |
||||
return new SyncUnaryClientRunner(channel, config.PayloadConfig.SimpleParams.ReqSize); |
||||
|
||||
case RpcType.STREAMING: |
||||
default: |
||||
throw new ArgumentException("Unsupported RpcType."); |
||||
} |
||||
} |
||||
} |
||||
|
||||
/// <summary> |
||||
/// Client that starts synchronous unary calls in a closed loop. |
||||
/// </summary> |
||||
public class SyncUnaryClientRunner : IClientRunner |
||||
{ |
||||
readonly Channel channel; |
||||
readonly int payloadSize; |
||||
readonly Histogram histogram; |
||||
|
||||
readonly BenchmarkService.IBenchmarkServiceClient client; |
||||
readonly Task runnerTask; |
||||
readonly CancellationTokenSource stoppedCts; |
||||
readonly WallClockStopwatch wallClockStopwatch = new WallClockStopwatch(); |
||||
|
||||
public SyncUnaryClientRunner(Channel channel, int payloadSize) |
||||
{ |
||||
this.channel = Grpc.Core.Utils.Preconditions.CheckNotNull(channel); |
||||
this.payloadSize = payloadSize; |
||||
this.histogram = new Histogram(0.01, 60e9); // TODO: needs to be in sync with test/cpp/qps/histogram.h |
||||
|
||||
this.stoppedCts = new CancellationTokenSource(); |
||||
this.client = BenchmarkService.NewClient(channel); |
||||
this.runnerTask = Task.Factory.StartNew(Run, TaskCreationOptions.LongRunning); |
||||
} |
||||
|
||||
public ClientStats GetStats(bool reset) |
||||
{ |
||||
var histogramData = histogram.GetSnapshot(reset); |
||||
var secondsElapsed = wallClockStopwatch.GetElapsedSnapshot(reset).TotalSeconds; |
||||
|
||||
// TODO: populate user time and system time |
||||
return new ClientStats |
||||
{ |
||||
Latencies = histogramData, |
||||
TimeElapsed = secondsElapsed, |
||||
TimeUser = 0, |
||||
TimeSystem = 0 |
||||
}; |
||||
} |
||||
|
||||
public async Task StopAsync() |
||||
{ |
||||
stoppedCts.Cancel(); |
||||
await runnerTask; |
||||
await channel.ShutdownAsync(); |
||||
} |
||||
|
||||
private void Run() |
||||
{ |
||||
var request = new SimpleRequest |
||||
{ |
||||
Payload = CreateZerosPayload(payloadSize) |
||||
}; |
||||
var stopwatch = new Stopwatch(); |
||||
|
||||
while (!stoppedCts.Token.IsCancellationRequested) |
||||
{ |
||||
stopwatch.Restart(); |
||||
client.UnaryCall(request); |
||||
stopwatch.Stop(); |
||||
|
||||
// TODO: 1e9 needs to be in sync with C++ code |
||||
histogram.AddObservation(stopwatch.Elapsed.TotalSeconds * 1e9); |
||||
} |
||||
} |
||||
|
||||
private static Payload CreateZerosPayload(int size) |
||||
{ |
||||
return new Payload { Body = ByteString.CopyFrom(new byte[size]) }; |
||||
} |
||||
} |
||||
} |
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,166 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.Diagnostics; |
||||
using System.IO; |
||||
using System.Linq; |
||||
using System.Text.RegularExpressions; |
||||
using System.Threading; |
||||
using System.Threading.Tasks; |
||||
using Google.Protobuf; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
using NUnit.Framework; |
||||
using Grpc.Testing; |
||||
|
||||
namespace Grpc.IntegrationTesting |
||||
{ |
||||
/// <summary> |
||||
/// Basic implementation of histogram based on grpc/support/histogram.h. |
||||
/// </summary> |
||||
public class Histogram |
||||
{ |
||||
readonly SpinLock spinlock = new SpinLock(); |
||||
|
||||
readonly double multiplier; |
||||
readonly double oneOnLogMultiplier; |
||||
readonly double maxPossible; |
||||
readonly uint[] buckets; |
||||
|
||||
int count; |
||||
double sum; |
||||
double sumOfSquares; |
||||
double min; |
||||
double max; |
||||
|
||||
public Histogram(double resolution, double maxPossible) |
||||
{ |
||||
Grpc.Core.Utils.Preconditions.CheckArgument(resolution > 0); |
||||
Grpc.Core.Utils.Preconditions.CheckArgument(maxPossible > 0); |
||||
this.maxPossible = maxPossible; |
||||
this.multiplier = 1.0 + resolution; |
||||
this.oneOnLogMultiplier = 1.0 / Math.Log(1.0 + resolution); |
||||
this.buckets = new uint[FindBucket(maxPossible) + 1]; |
||||
|
||||
ResetUnsafe(); |
||||
} |
||||
|
||||
public void AddObservation(double value) |
||||
{ |
||||
bool lockTaken = false; |
||||
spinlock.Enter(ref lockTaken); |
||||
try |
||||
{ |
||||
AddObservationUnsafe(value); |
||||
} |
||||
finally |
||||
{ |
||||
if (lockTaken) spinlock.Exit(); |
||||
} |
||||
} |
||||
|
||||
|
||||
/// <summary> |
||||
/// Gets snapshot of stats and reset |
||||
/// </summary> |
||||
public HistogramData GetSnapshot(bool reset = false) |
||||
{ |
||||
bool lockTaken = false; |
||||
spinlock.Enter(ref lockTaken); |
||||
try |
||||
{ |
||||
return GetSnapshotUnsafe(reset); |
||||
} |
||||
finally |
||||
{ |
||||
if (lockTaken) spinlock.Exit(); |
||||
} |
||||
} |
||||
|
||||
/// <summary> |
||||
/// Finds bucket index to which given observation should go. |
||||
/// </summary> |
||||
private int FindBucket(double value) |
||||
{ |
||||
value = Math.Max(value, 1.0); |
||||
value = Math.Min(value, this.maxPossible); |
||||
return (int)(Math.Log(value) * oneOnLogMultiplier); |
||||
} |
||||
|
||||
private void AddObservationUnsafe(double value) |
||||
{ |
||||
this.count++; |
||||
this.sum += value; |
||||
this.sumOfSquares += value * value; |
||||
this.min = Math.Min(this.min, value); |
||||
this.max = Math.Max(this.max, value); |
||||
|
||||
this.buckets[FindBucket(value)]++; |
||||
} |
||||
|
||||
private HistogramData GetSnapshotUnsafe(bool reset) |
||||
{ |
||||
var data = new HistogramData |
||||
{ |
||||
Count = count, |
||||
Sum = sum, |
||||
SumOfSquares = sumOfSquares, |
||||
MinSeen = min, |
||||
MaxSeen = max, |
||||
Bucket = { buckets } |
||||
}; |
||||
|
||||
if (reset) |
||||
{ |
||||
ResetUnsafe(); |
||||
} |
||||
|
||||
return data; |
||||
} |
||||
|
||||
private void ResetUnsafe() |
||||
{ |
||||
this.count = 0; |
||||
this.sum = 0; |
||||
this.sumOfSquares = 0; |
||||
this.min = double.PositiveInfinity; |
||||
this.max = double.NegativeInfinity; |
||||
for (int i = 0; i < this.buckets.Length; i++) |
||||
{ |
||||
this.buckets[i] = 0; |
||||
} |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,104 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.IO; |
||||
using System.Linq; |
||||
using System.Threading; |
||||
using System.Threading.Tasks; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
using Grpc.Testing; |
||||
using NUnit.Framework; |
||||
|
||||
namespace Grpc.IntegrationTesting |
||||
{ |
||||
public class HistogramTest |
||||
{ |
||||
[Test] |
||||
public void Simple() |
||||
{ |
||||
var hist = new Histogram(0.01, 60e9); |
||||
hist.AddObservation(10000); |
||||
hist.AddObservation(10000); |
||||
hist.AddObservation(11000); |
||||
hist.AddObservation(11000); |
||||
|
||||
var data = hist.GetSnapshot(); |
||||
|
||||
Assert.AreEqual(4, data.Count); |
||||
Assert.AreEqual(42000.0, data.Sum, 1e-6); |
||||
Assert.AreEqual(10000, data.MinSeen); |
||||
Assert.AreEqual(11000, data.MaxSeen); |
||||
Assert.AreEqual(2.0*10000*10000 + 2.0*11000*11000, data.SumOfSquares, 1e-6); |
||||
|
||||
// 1.01^925 < 10000 < 1.01^926 |
||||
Assert.AreEqual(2, data.Bucket[925]); |
||||
Assert.AreEqual(2, data.Bucket[935]); |
||||
} |
||||
|
||||
[Test] |
||||
public void ExtremeObservations() |
||||
{ |
||||
var hist = new Histogram(0.01, 60e9); |
||||
hist.AddObservation(-0.5); // should be in the first bucket |
||||
hist.AddObservation(1e12); // should be in the last bucket |
||||
|
||||
var data = hist.GetSnapshot(); |
||||
Assert.AreEqual(1, data.Bucket[0]); |
||||
Assert.AreEqual(1, data.Bucket[data.Bucket.Count - 1]); |
||||
} |
||||
|
||||
[Test] |
||||
public void Reset() |
||||
{ |
||||
var hist = new Histogram(0.01, 60e9); |
||||
hist.AddObservation(10000); |
||||
hist.AddObservation(11000); |
||||
|
||||
var data = hist.GetSnapshot(true); // snapshot contains data before reset |
||||
Assert.AreEqual(2, data.Count); |
||||
Assert.AreEqual(10000, data.MinSeen); |
||||
Assert.AreEqual(11000, data.MaxSeen); |
||||
|
||||
data = hist.GetSnapshot(); // snapshot contains state after reset |
||||
Assert.AreEqual(0, data.Count); |
||||
Assert.AreEqual(double.PositiveInfinity, data.MinSeen); |
||||
Assert.AreEqual(double.NegativeInfinity, data.MaxSeen); |
||||
Assert.AreEqual(0, data.Sum); |
||||
Assert.AreEqual(0, data.SumOfSquares); |
||||
CollectionAssert.AreEqual(new uint[data.Bucket.Count], data.Bucket); |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,67 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.Diagnostics; |
||||
using System.IO; |
||||
using System.Linq; |
||||
using System.Text.RegularExpressions; |
||||
using System.Threading.Tasks; |
||||
using Google.Protobuf; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
using NUnit.Framework; |
||||
using Grpc.Testing; |
||||
|
||||
namespace Grpc.IntegrationTesting |
||||
{ |
||||
/// <summary> |
||||
/// Abstract client runner. |
||||
/// </summary> |
||||
public interface IClientRunner |
||||
{ |
||||
/// <summary> |
||||
/// Gets stats snapshot. |
||||
/// </summary> |
||||
/// <returns>The stats.</returns> |
||||
ClientStats GetStats(bool reset); |
||||
|
||||
/// <summary> |
||||
/// Asynchronously stops the client. |
||||
/// </summary> |
||||
/// <returns>Task that finishes when client has come to a full stop.</returns> |
||||
Task StopAsync(); |
||||
} |
||||
|
||||
} |
@ -0,0 +1,72 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.Diagnostics; |
||||
using System.IO; |
||||
using System.Linq; |
||||
using System.Text.RegularExpressions; |
||||
using System.Threading.Tasks; |
||||
using Google.Protobuf; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
using NUnit.Framework; |
||||
using Grpc.Testing; |
||||
|
||||
namespace Grpc.IntegrationTesting |
||||
{ |
||||
/// <summary> |
||||
/// Abstract server runner. |
||||
/// </summary> |
||||
public interface IServerRunner |
||||
{ |
||||
/// <summary> |
||||
/// Port on which the server is listening. |
||||
/// </summary> |
||||
int BoundPort { get; } |
||||
|
||||
/// <summary> |
||||
/// Gets server stats. |
||||
/// </summary> |
||||
/// <returns>The stats.</returns> |
||||
ServerStats GetStats(bool reset); |
||||
|
||||
/// <summary> |
||||
/// Asynchronously stops the server. |
||||
/// </summary> |
||||
/// <returns>Task that finishes when server has shutdown.</returns> |
||||
Task StopAsync(); |
||||
} |
||||
|
||||
} |
@ -0,0 +1,580 @@ |
||||
// Generated by the protocol buffer compiler. DO NOT EDIT! |
||||
// source: test/proto/benchmarks/payloads.proto |
||||
#pragma warning disable 1591, 0612, 3021 |
||||
#region Designer generated code |
||||
|
||||
using pb = global::Google.Protobuf; |
||||
using pbc = global::Google.Protobuf.Collections; |
||||
using pbr = global::Google.Protobuf.Reflection; |
||||
using scg = global::System.Collections.Generic; |
||||
namespace Grpc.Testing { |
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()] |
||||
public static partial class Payloads { |
||||
|
||||
#region Descriptor |
||||
public static pbr::FileDescriptor Descriptor { |
||||
get { return descriptor; } |
||||
} |
||||
private static pbr::FileDescriptor descriptor; |
||||
|
||||
static Payloads() { |
||||
byte[] descriptorData = global::System.Convert.FromBase64String( |
||||
string.Concat( |
||||
"CiR0ZXN0L3Byb3RvL2JlbmNobWFya3MvcGF5bG9hZHMucHJvdG8SDGdycGMu", |
||||
"dGVzdGluZyI3ChBCeXRlQnVmZmVyUGFyYW1zEhAKCHJlcV9zaXplGAEgASgF", |
||||
"EhEKCXJlc3Bfc2l6ZRgCIAEoBSI4ChFTaW1wbGVQcm90b1BhcmFtcxIQCghy", |
||||
"ZXFfc2l6ZRgBIAEoBRIRCglyZXNwX3NpemUYAiABKAUiFAoSQ29tcGxleFBy", |
||||
"b3RvUGFyYW1zIsoBCg1QYXlsb2FkQ29uZmlnEjgKDmJ5dGVidWZfcGFyYW1z", |
||||
"GAEgASgLMh4uZ3JwYy50ZXN0aW5nLkJ5dGVCdWZmZXJQYXJhbXNIABI4Cg1z", |
||||
"aW1wbGVfcGFyYW1zGAIgASgLMh8uZ3JwYy50ZXN0aW5nLlNpbXBsZVByb3Rv", |
||||
"UGFyYW1zSAASOgoOY29tcGxleF9wYXJhbXMYAyABKAsyIC5ncnBjLnRlc3Rp", |
||||
"bmcuQ29tcGxleFByb3RvUGFyYW1zSABCCQoHcGF5bG9hZGIGcHJvdG8z")); |
||||
descriptor = pbr::FileDescriptor.InternalBuildGeneratedFileFrom(descriptorData, |
||||
new pbr::FileDescriptor[] { }, |
||||
new pbr::GeneratedCodeInfo(null, new pbr::GeneratedCodeInfo[] { |
||||
new pbr::GeneratedCodeInfo(typeof(global::Grpc.Testing.ByteBufferParams), new[]{ "ReqSize", "RespSize" }, null, null, null), |
||||
new pbr::GeneratedCodeInfo(typeof(global::Grpc.Testing.SimpleProtoParams), new[]{ "ReqSize", "RespSize" }, null, null, null), |
||||
new pbr::GeneratedCodeInfo(typeof(global::Grpc.Testing.ComplexProtoParams), null, null, null, null), |
||||
new pbr::GeneratedCodeInfo(typeof(global::Grpc.Testing.PayloadConfig), new[]{ "BytebufParams", "SimpleParams", "ComplexParams" }, new[]{ "Payload" }, null, null) |
||||
})); |
||||
} |
||||
#endregion |
||||
|
||||
} |
||||
#region Messages |
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()] |
||||
public sealed partial class ByteBufferParams : pb::IMessage<ByteBufferParams> { |
||||
private static readonly pb::MessageParser<ByteBufferParams> _parser = new pb::MessageParser<ByteBufferParams>(() => new ByteBufferParams()); |
||||
public static pb::MessageParser<ByteBufferParams> Parser { get { return _parser; } } |
||||
|
||||
public static pbr::MessageDescriptor Descriptor { |
||||
get { return global::Grpc.Testing.Payloads.Descriptor.MessageTypes[0]; } |
||||
} |
||||
|
||||
pbr::MessageDescriptor pb::IMessage.Descriptor { |
||||
get { return Descriptor; } |
||||
} |
||||
|
||||
public ByteBufferParams() { |
||||
OnConstruction(); |
||||
} |
||||
|
||||
partial void OnConstruction(); |
||||
|
||||
public ByteBufferParams(ByteBufferParams other) : this() { |
||||
reqSize_ = other.reqSize_; |
||||
respSize_ = other.respSize_; |
||||
} |
||||
|
||||
public ByteBufferParams Clone() { |
||||
return new ByteBufferParams(this); |
||||
} |
||||
|
||||
public const int ReqSizeFieldNumber = 1; |
||||
private int reqSize_; |
||||
public int ReqSize { |
||||
get { return reqSize_; } |
||||
set { |
||||
reqSize_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int RespSizeFieldNumber = 2; |
||||
private int respSize_; |
||||
public int RespSize { |
||||
get { return respSize_; } |
||||
set { |
||||
respSize_ = value; |
||||
} |
||||
} |
||||
|
||||
public override bool Equals(object other) { |
||||
return Equals(other as ByteBufferParams); |
||||
} |
||||
|
||||
public bool Equals(ByteBufferParams other) { |
||||
if (ReferenceEquals(other, null)) { |
||||
return false; |
||||
} |
||||
if (ReferenceEquals(other, this)) { |
||||
return true; |
||||
} |
||||
if (ReqSize != other.ReqSize) return false; |
||||
if (RespSize != other.RespSize) return false; |
||||
return true; |
||||
} |
||||
|
||||
public override int GetHashCode() { |
||||
int hash = 1; |
||||
if (ReqSize != 0) hash ^= ReqSize.GetHashCode(); |
||||
if (RespSize != 0) hash ^= RespSize.GetHashCode(); |
||||
return hash; |
||||
} |
||||
|
||||
public override string ToString() { |
||||
return pb::JsonFormatter.Default.Format(this); |
||||
} |
||||
|
||||
public void WriteTo(pb::CodedOutputStream output) { |
||||
if (ReqSize != 0) { |
||||
output.WriteRawTag(8); |
||||
output.WriteInt32(ReqSize); |
||||
} |
||||
if (RespSize != 0) { |
||||
output.WriteRawTag(16); |
||||
output.WriteInt32(RespSize); |
||||
} |
||||
} |
||||
|
||||
public int CalculateSize() { |
||||
int size = 0; |
||||
if (ReqSize != 0) { |
||||
size += 1 + pb::CodedOutputStream.ComputeInt32Size(ReqSize); |
||||
} |
||||
if (RespSize != 0) { |
||||
size += 1 + pb::CodedOutputStream.ComputeInt32Size(RespSize); |
||||
} |
||||
return size; |
||||
} |
||||
|
||||
public void MergeFrom(ByteBufferParams other) { |
||||
if (other == null) { |
||||
return; |
||||
} |
||||
if (other.ReqSize != 0) { |
||||
ReqSize = other.ReqSize; |
||||
} |
||||
if (other.RespSize != 0) { |
||||
RespSize = other.RespSize; |
||||
} |
||||
} |
||||
|
||||
public void MergeFrom(pb::CodedInputStream input) { |
||||
uint tag; |
||||
while ((tag = input.ReadTag()) != 0) { |
||||
switch(tag) { |
||||
default: |
||||
input.SkipLastField(); |
||||
break; |
||||
case 8: { |
||||
ReqSize = input.ReadInt32(); |
||||
break; |
||||
} |
||||
case 16: { |
||||
RespSize = input.ReadInt32(); |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
} |
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()] |
||||
public sealed partial class SimpleProtoParams : pb::IMessage<SimpleProtoParams> { |
||||
private static readonly pb::MessageParser<SimpleProtoParams> _parser = new pb::MessageParser<SimpleProtoParams>(() => new SimpleProtoParams()); |
||||
public static pb::MessageParser<SimpleProtoParams> Parser { get { return _parser; } } |
||||
|
||||
public static pbr::MessageDescriptor Descriptor { |
||||
get { return global::Grpc.Testing.Payloads.Descriptor.MessageTypes[1]; } |
||||
} |
||||
|
||||
pbr::MessageDescriptor pb::IMessage.Descriptor { |
||||
get { return Descriptor; } |
||||
} |
||||
|
||||
public SimpleProtoParams() { |
||||
OnConstruction(); |
||||
} |
||||
|
||||
partial void OnConstruction(); |
||||
|
||||
public SimpleProtoParams(SimpleProtoParams other) : this() { |
||||
reqSize_ = other.reqSize_; |
||||
respSize_ = other.respSize_; |
||||
} |
||||
|
||||
public SimpleProtoParams Clone() { |
||||
return new SimpleProtoParams(this); |
||||
} |
||||
|
||||
public const int ReqSizeFieldNumber = 1; |
||||
private int reqSize_; |
||||
public int ReqSize { |
||||
get { return reqSize_; } |
||||
set { |
||||
reqSize_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int RespSizeFieldNumber = 2; |
||||
private int respSize_; |
||||
public int RespSize { |
||||
get { return respSize_; } |
||||
set { |
||||
respSize_ = value; |
||||
} |
||||
} |
||||
|
||||
public override bool Equals(object other) { |
||||
return Equals(other as SimpleProtoParams); |
||||
} |
||||
|
||||
public bool Equals(SimpleProtoParams other) { |
||||
if (ReferenceEquals(other, null)) { |
||||
return false; |
||||
} |
||||
if (ReferenceEquals(other, this)) { |
||||
return true; |
||||
} |
||||
if (ReqSize != other.ReqSize) return false; |
||||
if (RespSize != other.RespSize) return false; |
||||
return true; |
||||
} |
||||
|
||||
public override int GetHashCode() { |
||||
int hash = 1; |
||||
if (ReqSize != 0) hash ^= ReqSize.GetHashCode(); |
||||
if (RespSize != 0) hash ^= RespSize.GetHashCode(); |
||||
return hash; |
||||
} |
||||
|
||||
public override string ToString() { |
||||
return pb::JsonFormatter.Default.Format(this); |
||||
} |
||||
|
||||
public void WriteTo(pb::CodedOutputStream output) { |
||||
if (ReqSize != 0) { |
||||
output.WriteRawTag(8); |
||||
output.WriteInt32(ReqSize); |
||||
} |
||||
if (RespSize != 0) { |
||||
output.WriteRawTag(16); |
||||
output.WriteInt32(RespSize); |
||||
} |
||||
} |
||||
|
||||
public int CalculateSize() { |
||||
int size = 0; |
||||
if (ReqSize != 0) { |
||||
size += 1 + pb::CodedOutputStream.ComputeInt32Size(ReqSize); |
||||
} |
||||
if (RespSize != 0) { |
||||
size += 1 + pb::CodedOutputStream.ComputeInt32Size(RespSize); |
||||
} |
||||
return size; |
||||
} |
||||
|
||||
public void MergeFrom(SimpleProtoParams other) { |
||||
if (other == null) { |
||||
return; |
||||
} |
||||
if (other.ReqSize != 0) { |
||||
ReqSize = other.ReqSize; |
||||
} |
||||
if (other.RespSize != 0) { |
||||
RespSize = other.RespSize; |
||||
} |
||||
} |
||||
|
||||
public void MergeFrom(pb::CodedInputStream input) { |
||||
uint tag; |
||||
while ((tag = input.ReadTag()) != 0) { |
||||
switch(tag) { |
||||
default: |
||||
input.SkipLastField(); |
||||
break; |
||||
case 8: { |
||||
ReqSize = input.ReadInt32(); |
||||
break; |
||||
} |
||||
case 16: { |
||||
RespSize = input.ReadInt32(); |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
} |
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()] |
||||
public sealed partial class ComplexProtoParams : pb::IMessage<ComplexProtoParams> { |
||||
private static readonly pb::MessageParser<ComplexProtoParams> _parser = new pb::MessageParser<ComplexProtoParams>(() => new ComplexProtoParams()); |
||||
public static pb::MessageParser<ComplexProtoParams> Parser { get { return _parser; } } |
||||
|
||||
public static pbr::MessageDescriptor Descriptor { |
||||
get { return global::Grpc.Testing.Payloads.Descriptor.MessageTypes[2]; } |
||||
} |
||||
|
||||
pbr::MessageDescriptor pb::IMessage.Descriptor { |
||||
get { return Descriptor; } |
||||
} |
||||
|
||||
public ComplexProtoParams() { |
||||
OnConstruction(); |
||||
} |
||||
|
||||
partial void OnConstruction(); |
||||
|
||||
public ComplexProtoParams(ComplexProtoParams other) : this() { |
||||
} |
||||
|
||||
public ComplexProtoParams Clone() { |
||||
return new ComplexProtoParams(this); |
||||
} |
||||
|
||||
public override bool Equals(object other) { |
||||
return Equals(other as ComplexProtoParams); |
||||
} |
||||
|
||||
public bool Equals(ComplexProtoParams other) { |
||||
if (ReferenceEquals(other, null)) { |
||||
return false; |
||||
} |
||||
if (ReferenceEquals(other, this)) { |
||||
return true; |
||||
} |
||||
return true; |
||||
} |
||||
|
||||
public override int GetHashCode() { |
||||
int hash = 1; |
||||
return hash; |
||||
} |
||||
|
||||
public override string ToString() { |
||||
return pb::JsonFormatter.Default.Format(this); |
||||
} |
||||
|
||||
public void WriteTo(pb::CodedOutputStream output) { |
||||
} |
||||
|
||||
public int CalculateSize() { |
||||
int size = 0; |
||||
return size; |
||||
} |
||||
|
||||
public void MergeFrom(ComplexProtoParams other) { |
||||
if (other == null) { |
||||
return; |
||||
} |
||||
} |
||||
|
||||
public void MergeFrom(pb::CodedInputStream input) { |
||||
uint tag; |
||||
while ((tag = input.ReadTag()) != 0) { |
||||
switch(tag) { |
||||
default: |
||||
input.SkipLastField(); |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
|
||||
} |
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()] |
||||
public sealed partial class PayloadConfig : pb::IMessage<PayloadConfig> { |
||||
private static readonly pb::MessageParser<PayloadConfig> _parser = new pb::MessageParser<PayloadConfig>(() => new PayloadConfig()); |
||||
public static pb::MessageParser<PayloadConfig> Parser { get { return _parser; } } |
||||
|
||||
public static pbr::MessageDescriptor Descriptor { |
||||
get { return global::Grpc.Testing.Payloads.Descriptor.MessageTypes[3]; } |
||||
} |
||||
|
||||
pbr::MessageDescriptor pb::IMessage.Descriptor { |
||||
get { return Descriptor; } |
||||
} |
||||
|
||||
public PayloadConfig() { |
||||
OnConstruction(); |
||||
} |
||||
|
||||
partial void OnConstruction(); |
||||
|
||||
public PayloadConfig(PayloadConfig other) : this() { |
||||
switch (other.PayloadCase) { |
||||
case PayloadOneofCase.BytebufParams: |
||||
BytebufParams = other.BytebufParams.Clone(); |
||||
break; |
||||
case PayloadOneofCase.SimpleParams: |
||||
SimpleParams = other.SimpleParams.Clone(); |
||||
break; |
||||
case PayloadOneofCase.ComplexParams: |
||||
ComplexParams = other.ComplexParams.Clone(); |
||||
break; |
||||
} |
||||
|
||||
} |
||||
|
||||
public PayloadConfig Clone() { |
||||
return new PayloadConfig(this); |
||||
} |
||||
|
||||
public const int BytebufParamsFieldNumber = 1; |
||||
public global::Grpc.Testing.ByteBufferParams BytebufParams { |
||||
get { return payloadCase_ == PayloadOneofCase.BytebufParams ? (global::Grpc.Testing.ByteBufferParams) payload_ : null; } |
||||
set { |
||||
payload_ = value; |
||||
payloadCase_ = value == null ? PayloadOneofCase.None : PayloadOneofCase.BytebufParams; |
||||
} |
||||
} |
||||
|
||||
public const int SimpleParamsFieldNumber = 2; |
||||
public global::Grpc.Testing.SimpleProtoParams SimpleParams { |
||||
get { return payloadCase_ == PayloadOneofCase.SimpleParams ? (global::Grpc.Testing.SimpleProtoParams) payload_ : null; } |
||||
set { |
||||
payload_ = value; |
||||
payloadCase_ = value == null ? PayloadOneofCase.None : PayloadOneofCase.SimpleParams; |
||||
} |
||||
} |
||||
|
||||
public const int ComplexParamsFieldNumber = 3; |
||||
public global::Grpc.Testing.ComplexProtoParams ComplexParams { |
||||
get { return payloadCase_ == PayloadOneofCase.ComplexParams ? (global::Grpc.Testing.ComplexProtoParams) payload_ : null; } |
||||
set { |
||||
payload_ = value; |
||||
payloadCase_ = value == null ? PayloadOneofCase.None : PayloadOneofCase.ComplexParams; |
||||
} |
||||
} |
||||
|
||||
private object payload_; |
||||
public enum PayloadOneofCase { |
||||
None = 0, |
||||
BytebufParams = 1, |
||||
SimpleParams = 2, |
||||
ComplexParams = 3, |
||||
} |
||||
private PayloadOneofCase payloadCase_ = PayloadOneofCase.None; |
||||
public PayloadOneofCase PayloadCase { |
||||
get { return payloadCase_; } |
||||
} |
||||
|
||||
public void ClearPayload() { |
||||
payloadCase_ = PayloadOneofCase.None; |
||||
payload_ = null; |
||||
} |
||||
|
||||
public override bool Equals(object other) { |
||||
return Equals(other as PayloadConfig); |
||||
} |
||||
|
||||
public bool Equals(PayloadConfig other) { |
||||
if (ReferenceEquals(other, null)) { |
||||
return false; |
||||
} |
||||
if (ReferenceEquals(other, this)) { |
||||
return true; |
||||
} |
||||
if (!object.Equals(BytebufParams, other.BytebufParams)) return false; |
||||
if (!object.Equals(SimpleParams, other.SimpleParams)) return false; |
||||
if (!object.Equals(ComplexParams, other.ComplexParams)) return false; |
||||
return true; |
||||
} |
||||
|
||||
public override int GetHashCode() { |
||||
int hash = 1; |
||||
if (payloadCase_ == PayloadOneofCase.BytebufParams) hash ^= BytebufParams.GetHashCode(); |
||||
if (payloadCase_ == PayloadOneofCase.SimpleParams) hash ^= SimpleParams.GetHashCode(); |
||||
if (payloadCase_ == PayloadOneofCase.ComplexParams) hash ^= ComplexParams.GetHashCode(); |
||||
return hash; |
||||
} |
||||
|
||||
public override string ToString() { |
||||
return pb::JsonFormatter.Default.Format(this); |
||||
} |
||||
|
||||
public void WriteTo(pb::CodedOutputStream output) { |
||||
if (payloadCase_ == PayloadOneofCase.BytebufParams) { |
||||
output.WriteRawTag(10); |
||||
output.WriteMessage(BytebufParams); |
||||
} |
||||
if (payloadCase_ == PayloadOneofCase.SimpleParams) { |
||||
output.WriteRawTag(18); |
||||
output.WriteMessage(SimpleParams); |
||||
} |
||||
if (payloadCase_ == PayloadOneofCase.ComplexParams) { |
||||
output.WriteRawTag(26); |
||||
output.WriteMessage(ComplexParams); |
||||
} |
||||
} |
||||
|
||||
public int CalculateSize() { |
||||
int size = 0; |
||||
if (payloadCase_ == PayloadOneofCase.BytebufParams) { |
||||
size += 1 + pb::CodedOutputStream.ComputeMessageSize(BytebufParams); |
||||
} |
||||
if (payloadCase_ == PayloadOneofCase.SimpleParams) { |
||||
size += 1 + pb::CodedOutputStream.ComputeMessageSize(SimpleParams); |
||||
} |
||||
if (payloadCase_ == PayloadOneofCase.ComplexParams) { |
||||
size += 1 + pb::CodedOutputStream.ComputeMessageSize(ComplexParams); |
||||
} |
||||
return size; |
||||
} |
||||
|
||||
public void MergeFrom(PayloadConfig other) { |
||||
if (other == null) { |
||||
return; |
||||
} |
||||
switch (other.PayloadCase) { |
||||
case PayloadOneofCase.BytebufParams: |
||||
BytebufParams = other.BytebufParams; |
||||
break; |
||||
case PayloadOneofCase.SimpleParams: |
||||
SimpleParams = other.SimpleParams; |
||||
break; |
||||
case PayloadOneofCase.ComplexParams: |
||||
ComplexParams = other.ComplexParams; |
||||
break; |
||||
} |
||||
|
||||
} |
||||
|
||||
public void MergeFrom(pb::CodedInputStream input) { |
||||
uint tag; |
||||
while ((tag = input.ReadTag()) != 0) { |
||||
switch(tag) { |
||||
default: |
||||
input.SkipLastField(); |
||||
break; |
||||
case 10: { |
||||
global::Grpc.Testing.ByteBufferParams subBuilder = new global::Grpc.Testing.ByteBufferParams(); |
||||
if (payloadCase_ == PayloadOneofCase.BytebufParams) { |
||||
subBuilder.MergeFrom(BytebufParams); |
||||
} |
||||
input.ReadMessage(subBuilder); |
||||
BytebufParams = subBuilder; |
||||
break; |
||||
} |
||||
case 18: { |
||||
global::Grpc.Testing.SimpleProtoParams subBuilder = new global::Grpc.Testing.SimpleProtoParams(); |
||||
if (payloadCase_ == PayloadOneofCase.SimpleParams) { |
||||
subBuilder.MergeFrom(SimpleParams); |
||||
} |
||||
input.ReadMessage(subBuilder); |
||||
SimpleParams = subBuilder; |
||||
break; |
||||
} |
||||
case 26: { |
||||
global::Grpc.Testing.ComplexProtoParams subBuilder = new global::Grpc.Testing.ComplexProtoParams(); |
||||
if (payloadCase_ == PayloadOneofCase.ComplexParams) { |
||||
subBuilder.MergeFrom(ComplexParams); |
||||
} |
||||
input.ReadMessage(subBuilder); |
||||
ComplexParams = subBuilder; |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
} |
||||
|
||||
#endregion |
||||
|
||||
} |
||||
|
||||
#endregion Designer generated code |
@ -0,0 +1,108 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.Diagnostics; |
||||
using System.IO; |
||||
using System.Linq; |
||||
using System.Text.RegularExpressions; |
||||
using System.Threading.Tasks; |
||||
|
||||
using CommandLine; |
||||
using CommandLine.Text; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
using Grpc.Testing; |
||||
using NUnit.Framework; |
||||
|
||||
namespace Grpc.IntegrationTesting |
||||
{ |
||||
public class QpsWorker |
||||
{ |
||||
private class ServerOptions |
||||
{ |
||||
[Option("driver_port", DefaultValue = 0)] |
||||
public int DriverPort { get; set; } |
||||
|
||||
[HelpOption] |
||||
public string GetUsage() |
||||
{ |
||||
var help = new HelpText |
||||
{ |
||||
Heading = "gRPC C# performance testing worker", |
||||
AddDashesToOption = true |
||||
}; |
||||
help.AddPreOptionsLine("Usage:"); |
||||
help.AddOptions(this); |
||||
return help; |
||||
} |
||||
} |
||||
|
||||
ServerOptions options; |
||||
|
||||
private QpsWorker(ServerOptions options) |
||||
{ |
||||
this.options = options; |
||||
} |
||||
|
||||
public static void Run(string[] args) |
||||
{ |
||||
var options = new ServerOptions(); |
||||
if (!Parser.Default.ParseArguments(args, options)) |
||||
{ |
||||
Environment.Exit(1); |
||||
} |
||||
|
||||
var workerServer = new QpsWorker(options); |
||||
workerServer.Run(); |
||||
} |
||||
|
||||
private void Run() |
||||
{ |
||||
string host = "0.0.0.0"; |
||||
int port = options.DriverPort; |
||||
|
||||
var server = new Server |
||||
{ |
||||
Services = { WorkerService.BindService(new WorkerServiceImpl()) }, |
||||
Ports = { new ServerPort(host, options.DriverPort, ServerCredentials.Insecure )} |
||||
}; |
||||
int boundPort = server.Ports.Single().BoundPort; |
||||
Console.WriteLine("Running qps worker server on " + string.Format("{0}:{1}", host, boundPort)); |
||||
server.Start(); |
||||
|
||||
server.ShutdownTask.Wait(); |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,109 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.Linq; |
||||
using System.Threading; |
||||
using System.Threading.Tasks; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
using Grpc.Testing; |
||||
using NUnit.Framework; |
||||
|
||||
namespace Grpc.IntegrationTesting |
||||
{ |
||||
/// <summary> |
||||
/// Runs performance tests in-process. |
||||
/// </summary> |
||||
public class RunnerClientServerTest |
||||
{ |
||||
const string Host = "localhost"; |
||||
IServerRunner serverRunner; |
||||
|
||||
[TestFixtureSetUp] |
||||
public void Init() |
||||
{ |
||||
var serverConfig = new ServerConfig |
||||
{ |
||||
ServerType = ServerType.ASYNC_SERVER, |
||||
PayloadConfig = new PayloadConfig |
||||
{ |
||||
SimpleParams = new SimpleProtoParams |
||||
{ |
||||
RespSize = 100 |
||||
} |
||||
} |
||||
}; |
||||
serverRunner = ServerRunners.CreateStarted(serverConfig); |
||||
} |
||||
|
||||
[TestFixtureTearDown] |
||||
public void Cleanup() |
||||
{ |
||||
serverRunner.StopAsync().Wait(); |
||||
} |
||||
|
||||
[Test] |
||||
public async Task ClientServerRunner() |
||||
{ |
||||
var config = new ClientConfig |
||||
{ |
||||
ServerTargets = { string.Format("{0}:{1}", Host, serverRunner.BoundPort) }, |
||||
RpcType = RpcType.UNARY, |
||||
LoadParams = new LoadParams { ClosedLoop = new ClosedLoopParams() }, |
||||
PayloadConfig = new PayloadConfig |
||||
{ |
||||
SimpleParams = new SimpleProtoParams |
||||
{ |
||||
ReqSize = 100 |
||||
} |
||||
} |
||||
}; |
||||
|
||||
var runner = ClientRunners.CreateStarted(config); |
||||
|
||||
System.Console.WriteLine("Warming up"); |
||||
await Task.Delay(3000); |
||||
runner.GetStats(true); // throw away warm-up data |
||||
|
||||
System.Console.WriteLine("Benchmarking"); |
||||
await Task.Delay(3000); |
||||
var stats = runner.GetStats(true); |
||||
await runner.StopAsync(); |
||||
|
||||
System.Console.WriteLine(stats); |
||||
System.Console.WriteLine("avg micros/call " + (long) ((stats.Latencies.Sum / stats.Latencies.Count) * 1000000)); |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,124 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.Diagnostics; |
||||
using System.IO; |
||||
using System.Linq; |
||||
using System.Text.RegularExpressions; |
||||
using System.Threading; |
||||
using System.Threading.Tasks; |
||||
using Google.Protobuf; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
using NUnit.Framework; |
||||
using Grpc.Testing; |
||||
|
||||
namespace Grpc.IntegrationTesting |
||||
{ |
||||
/// <summary> |
||||
/// Helper methods to start server runners for performance testing. |
||||
/// </summary> |
||||
public static class ServerRunners |
||||
{ |
||||
/// <summary> |
||||
/// Creates a started server runner. |
||||
/// </summary> |
||||
public static IServerRunner CreateStarted(ServerConfig config) |
||||
{ |
||||
Grpc.Core.Utils.Preconditions.CheckArgument(config.ServerType == ServerType.ASYNC_SERVER); |
||||
var credentials = config.SecurityParams != null ? TestCredentials.CreateSslServerCredentials() : ServerCredentials.Insecure; |
||||
|
||||
// TODO: qps_driver needs to setup payload properly... |
||||
int responseSize = config.PayloadConfig != null ? config.PayloadConfig.SimpleParams.RespSize : 0; |
||||
var server = new Server |
||||
{ |
||||
Services = { BenchmarkService.BindService(new BenchmarkServiceImpl(responseSize)) }, |
||||
Ports = { new ServerPort("0.0.0.0", config.Port, credentials) } |
||||
}; |
||||
|
||||
server.Start(); |
||||
return new ServerRunnerImpl(server); |
||||
} |
||||
} |
||||
|
||||
/// <summary> |
||||
/// Server runner. |
||||
/// </summary> |
||||
public class ServerRunnerImpl : IServerRunner |
||||
{ |
||||
readonly Server server; |
||||
readonly WallClockStopwatch wallClockStopwatch = new WallClockStopwatch(); |
||||
|
||||
public ServerRunnerImpl(Server server) |
||||
{ |
||||
this.server = Grpc.Core.Utils.Preconditions.CheckNotNull(server); |
||||
} |
||||
|
||||
public int BoundPort |
||||
{ |
||||
get |
||||
{ |
||||
return server.Ports.Single().BoundPort; |
||||
} |
||||
} |
||||
|
||||
/// <summary> |
||||
/// Gets server stats. |
||||
/// </summary> |
||||
/// <returns>The stats.</returns> |
||||
public ServerStats GetStats(bool reset) |
||||
{ |
||||
var secondsElapsed = wallClockStopwatch.GetElapsedSnapshot(reset).TotalSeconds; |
||||
|
||||
// TODO: populate user time and system time |
||||
return new ServerStats |
||||
{ |
||||
TimeElapsed = secondsElapsed, |
||||
TimeUser = 0, |
||||
TimeSystem = 0 |
||||
}; |
||||
} |
||||
|
||||
/// <summary> |
||||
/// Asynchronously stops the server. |
||||
/// </summary> |
||||
/// <returns>Task that finishes when server has shutdown.</returns> |
||||
public Task StopAsync() |
||||
{ |
||||
return server.ShutdownAsync(); |
||||
} |
||||
} |
||||
|
||||
} |
@ -0,0 +1,44 @@ |
||||
// Generated by the protocol buffer compiler. DO NOT EDIT! |
||||
// source: test/proto/benchmarks/services.proto |
||||
#pragma warning disable 1591, 0612, 3021 |
||||
#region Designer generated code |
||||
|
||||
using pb = global::Google.Protobuf; |
||||
using pbc = global::Google.Protobuf.Collections; |
||||
using pbr = global::Google.Protobuf.Reflection; |
||||
using scg = global::System.Collections.Generic; |
||||
namespace Grpc.Testing { |
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()] |
||||
public static partial class Services { |
||||
|
||||
#region Descriptor |
||||
public static pbr::FileDescriptor Descriptor { |
||||
get { return descriptor; } |
||||
} |
||||
private static pbr::FileDescriptor descriptor; |
||||
|
||||
static Services() { |
||||
byte[] descriptorData = global::System.Convert.FromBase64String( |
||||
string.Concat( |
||||
"CiR0ZXN0L3Byb3RvL2JlbmNobWFya3Mvc2VydmljZXMucHJvdG8SDGdycGMu", |
||||
"dGVzdGluZxoZdGVzdC9wcm90by9tZXNzYWdlcy5wcm90bxojdGVzdC9wcm90", |
||||
"by9iZW5jaG1hcmtzL2NvbnRyb2wucHJvdG8yqgEKEEJlbmNobWFya1NlcnZp", |
||||
"Y2USRgoJVW5hcnlDYWxsEhsuZ3JwYy50ZXN0aW5nLlNpbXBsZVJlcXVlc3Qa", |
||||
"HC5ncnBjLnRlc3RpbmcuU2ltcGxlUmVzcG9uc2USTgoNU3RyZWFtaW5nQ2Fs", |
||||
"bBIbLmdycGMudGVzdGluZy5TaW1wbGVSZXF1ZXN0GhwuZ3JwYy50ZXN0aW5n", |
||||
"LlNpbXBsZVJlc3BvbnNlKAEwATKdAQoNV29ya2VyU2VydmljZRJFCglSdW5T", |
||||
"ZXJ2ZXISGC5ncnBjLnRlc3RpbmcuU2VydmVyQXJncxoaLmdycGMudGVzdGlu", |
||||
"Zy5TZXJ2ZXJTdGF0dXMoATABEkUKCVJ1bkNsaWVudBIYLmdycGMudGVzdGlu", |
||||
"Zy5DbGllbnRBcmdzGhouZ3JwYy50ZXN0aW5nLkNsaWVudFN0YXR1cygBMAFi", |
||||
"BnByb3RvMw==")); |
||||
descriptor = pbr::FileDescriptor.InternalBuildGeneratedFileFrom(descriptorData, |
||||
new pbr::FileDescriptor[] { global::Grpc.Testing.Messages.Descriptor, global::Grpc.Testing.Control.Descriptor, }, |
||||
new pbr::GeneratedCodeInfo(null, null)); |
||||
} |
||||
#endregion |
||||
|
||||
} |
||||
} |
||||
|
||||
#endregion Designer generated code |
@ -0,0 +1,198 @@ |
||||
// Generated by the protocol buffer compiler. DO NOT EDIT! |
||||
// source: test/proto/benchmarks/services.proto |
||||
#region Designer generated code |
||||
|
||||
using System; |
||||
using System.Threading; |
||||
using System.Threading.Tasks; |
||||
using Grpc.Core; |
||||
|
||||
namespace Grpc.Testing { |
||||
public static class BenchmarkService |
||||
{ |
||||
static readonly string __ServiceName = "grpc.testing.BenchmarkService"; |
||||
|
||||
static readonly Marshaller<global::Grpc.Testing.SimpleRequest> __Marshaller_SimpleRequest = Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Grpc.Testing.SimpleRequest.Parser.ParseFrom); |
||||
static readonly Marshaller<global::Grpc.Testing.SimpleResponse> __Marshaller_SimpleResponse = Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Grpc.Testing.SimpleResponse.Parser.ParseFrom); |
||||
|
||||
static readonly Method<global::Grpc.Testing.SimpleRequest, global::Grpc.Testing.SimpleResponse> __Method_UnaryCall = new Method<global::Grpc.Testing.SimpleRequest, global::Grpc.Testing.SimpleResponse>( |
||||
MethodType.Unary, |
||||
__ServiceName, |
||||
"UnaryCall", |
||||
__Marshaller_SimpleRequest, |
||||
__Marshaller_SimpleResponse); |
||||
|
||||
static readonly Method<global::Grpc.Testing.SimpleRequest, global::Grpc.Testing.SimpleResponse> __Method_StreamingCall = new Method<global::Grpc.Testing.SimpleRequest, global::Grpc.Testing.SimpleResponse>( |
||||
MethodType.DuplexStreaming, |
||||
__ServiceName, |
||||
"StreamingCall", |
||||
__Marshaller_SimpleRequest, |
||||
__Marshaller_SimpleResponse); |
||||
|
||||
// service descriptor |
||||
public static global::Google.Protobuf.Reflection.ServiceDescriptor Descriptor |
||||
{ |
||||
get { return global::Grpc.Testing.Services.Descriptor.Services[0]; } |
||||
} |
||||
|
||||
// client interface |
||||
public interface IBenchmarkServiceClient |
||||
{ |
||||
global::Grpc.Testing.SimpleResponse UnaryCall(global::Grpc.Testing.SimpleRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken)); |
||||
global::Grpc.Testing.SimpleResponse UnaryCall(global::Grpc.Testing.SimpleRequest request, CallOptions options); |
||||
AsyncUnaryCall<global::Grpc.Testing.SimpleResponse> UnaryCallAsync(global::Grpc.Testing.SimpleRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken)); |
||||
AsyncUnaryCall<global::Grpc.Testing.SimpleResponse> UnaryCallAsync(global::Grpc.Testing.SimpleRequest request, CallOptions options); |
||||
AsyncDuplexStreamingCall<global::Grpc.Testing.SimpleRequest, global::Grpc.Testing.SimpleResponse> StreamingCall(Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken)); |
||||
AsyncDuplexStreamingCall<global::Grpc.Testing.SimpleRequest, global::Grpc.Testing.SimpleResponse> StreamingCall(CallOptions options); |
||||
} |
||||
|
||||
// server-side interface |
||||
public interface IBenchmarkService |
||||
{ |
||||
Task<global::Grpc.Testing.SimpleResponse> UnaryCall(global::Grpc.Testing.SimpleRequest request, ServerCallContext context); |
||||
Task StreamingCall(IAsyncStreamReader<global::Grpc.Testing.SimpleRequest> requestStream, IServerStreamWriter<global::Grpc.Testing.SimpleResponse> responseStream, ServerCallContext context); |
||||
} |
||||
|
||||
// client stub |
||||
public class BenchmarkServiceClient : ClientBase, IBenchmarkServiceClient |
||||
{ |
||||
public BenchmarkServiceClient(Channel channel) : base(channel) |
||||
{ |
||||
} |
||||
public global::Grpc.Testing.SimpleResponse UnaryCall(global::Grpc.Testing.SimpleRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken)) |
||||
{ |
||||
var call = CreateCall(__Method_UnaryCall, new CallOptions(headers, deadline, cancellationToken)); |
||||
return Calls.BlockingUnaryCall(call, request); |
||||
} |
||||
public global::Grpc.Testing.SimpleResponse UnaryCall(global::Grpc.Testing.SimpleRequest request, CallOptions options) |
||||
{ |
||||
var call = CreateCall(__Method_UnaryCall, options); |
||||
return Calls.BlockingUnaryCall(call, request); |
||||
} |
||||
public AsyncUnaryCall<global::Grpc.Testing.SimpleResponse> UnaryCallAsync(global::Grpc.Testing.SimpleRequest request, Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken)) |
||||
{ |
||||
var call = CreateCall(__Method_UnaryCall, new CallOptions(headers, deadline, cancellationToken)); |
||||
return Calls.AsyncUnaryCall(call, request); |
||||
} |
||||
public AsyncUnaryCall<global::Grpc.Testing.SimpleResponse> UnaryCallAsync(global::Grpc.Testing.SimpleRequest request, CallOptions options) |
||||
{ |
||||
var call = CreateCall(__Method_UnaryCall, options); |
||||
return Calls.AsyncUnaryCall(call, request); |
||||
} |
||||
public AsyncDuplexStreamingCall<global::Grpc.Testing.SimpleRequest, global::Grpc.Testing.SimpleResponse> StreamingCall(Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken)) |
||||
{ |
||||
var call = CreateCall(__Method_StreamingCall, new CallOptions(headers, deadline, cancellationToken)); |
||||
return Calls.AsyncDuplexStreamingCall(call); |
||||
} |
||||
public AsyncDuplexStreamingCall<global::Grpc.Testing.SimpleRequest, global::Grpc.Testing.SimpleResponse> StreamingCall(CallOptions options) |
||||
{ |
||||
var call = CreateCall(__Method_StreamingCall, options); |
||||
return Calls.AsyncDuplexStreamingCall(call); |
||||
} |
||||
} |
||||
|
||||
// creates service definition that can be registered with a server |
||||
public static ServerServiceDefinition BindService(IBenchmarkService serviceImpl) |
||||
{ |
||||
return ServerServiceDefinition.CreateBuilder(__ServiceName) |
||||
.AddMethod(__Method_UnaryCall, serviceImpl.UnaryCall) |
||||
.AddMethod(__Method_StreamingCall, serviceImpl.StreamingCall).Build(); |
||||
} |
||||
|
||||
// creates a new client |
||||
public static BenchmarkServiceClient NewClient(Channel channel) |
||||
{ |
||||
return new BenchmarkServiceClient(channel); |
||||
} |
||||
|
||||
} |
||||
public static class WorkerService |
||||
{ |
||||
static readonly string __ServiceName = "grpc.testing.WorkerService"; |
||||
|
||||
static readonly Marshaller<global::Grpc.Testing.ServerArgs> __Marshaller_ServerArgs = Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Grpc.Testing.ServerArgs.Parser.ParseFrom); |
||||
static readonly Marshaller<global::Grpc.Testing.ServerStatus> __Marshaller_ServerStatus = Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Grpc.Testing.ServerStatus.Parser.ParseFrom); |
||||
static readonly Marshaller<global::Grpc.Testing.ClientArgs> __Marshaller_ClientArgs = Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Grpc.Testing.ClientArgs.Parser.ParseFrom); |
||||
static readonly Marshaller<global::Grpc.Testing.ClientStatus> __Marshaller_ClientStatus = Marshallers.Create((arg) => global::Google.Protobuf.MessageExtensions.ToByteArray(arg), global::Grpc.Testing.ClientStatus.Parser.ParseFrom); |
||||
|
||||
static readonly Method<global::Grpc.Testing.ServerArgs, global::Grpc.Testing.ServerStatus> __Method_RunServer = new Method<global::Grpc.Testing.ServerArgs, global::Grpc.Testing.ServerStatus>( |
||||
MethodType.DuplexStreaming, |
||||
__ServiceName, |
||||
"RunServer", |
||||
__Marshaller_ServerArgs, |
||||
__Marshaller_ServerStatus); |
||||
|
||||
static readonly Method<global::Grpc.Testing.ClientArgs, global::Grpc.Testing.ClientStatus> __Method_RunClient = new Method<global::Grpc.Testing.ClientArgs, global::Grpc.Testing.ClientStatus>( |
||||
MethodType.DuplexStreaming, |
||||
__ServiceName, |
||||
"RunClient", |
||||
__Marshaller_ClientArgs, |
||||
__Marshaller_ClientStatus); |
||||
|
||||
// service descriptor |
||||
public static global::Google.Protobuf.Reflection.ServiceDescriptor Descriptor |
||||
{ |
||||
get { return global::Grpc.Testing.Services.Descriptor.Services[1]; } |
||||
} |
||||
|
||||
// client interface |
||||
public interface IWorkerServiceClient |
||||
{ |
||||
AsyncDuplexStreamingCall<global::Grpc.Testing.ServerArgs, global::Grpc.Testing.ServerStatus> RunServer(Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken)); |
||||
AsyncDuplexStreamingCall<global::Grpc.Testing.ServerArgs, global::Grpc.Testing.ServerStatus> RunServer(CallOptions options); |
||||
AsyncDuplexStreamingCall<global::Grpc.Testing.ClientArgs, global::Grpc.Testing.ClientStatus> RunClient(Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken)); |
||||
AsyncDuplexStreamingCall<global::Grpc.Testing.ClientArgs, global::Grpc.Testing.ClientStatus> RunClient(CallOptions options); |
||||
} |
||||
|
||||
// server-side interface |
||||
public interface IWorkerService |
||||
{ |
||||
Task RunServer(IAsyncStreamReader<global::Grpc.Testing.ServerArgs> requestStream, IServerStreamWriter<global::Grpc.Testing.ServerStatus> responseStream, ServerCallContext context); |
||||
Task RunClient(IAsyncStreamReader<global::Grpc.Testing.ClientArgs> requestStream, IServerStreamWriter<global::Grpc.Testing.ClientStatus> responseStream, ServerCallContext context); |
||||
} |
||||
|
||||
// client stub |
||||
public class WorkerServiceClient : ClientBase, IWorkerServiceClient |
||||
{ |
||||
public WorkerServiceClient(Channel channel) : base(channel) |
||||
{ |
||||
} |
||||
public AsyncDuplexStreamingCall<global::Grpc.Testing.ServerArgs, global::Grpc.Testing.ServerStatus> RunServer(Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken)) |
||||
{ |
||||
var call = CreateCall(__Method_RunServer, new CallOptions(headers, deadline, cancellationToken)); |
||||
return Calls.AsyncDuplexStreamingCall(call); |
||||
} |
||||
public AsyncDuplexStreamingCall<global::Grpc.Testing.ServerArgs, global::Grpc.Testing.ServerStatus> RunServer(CallOptions options) |
||||
{ |
||||
var call = CreateCall(__Method_RunServer, options); |
||||
return Calls.AsyncDuplexStreamingCall(call); |
||||
} |
||||
public AsyncDuplexStreamingCall<global::Grpc.Testing.ClientArgs, global::Grpc.Testing.ClientStatus> RunClient(Metadata headers = null, DateTime? deadline = null, CancellationToken cancellationToken = default(CancellationToken)) |
||||
{ |
||||
var call = CreateCall(__Method_RunClient, new CallOptions(headers, deadline, cancellationToken)); |
||||
return Calls.AsyncDuplexStreamingCall(call); |
||||
} |
||||
public AsyncDuplexStreamingCall<global::Grpc.Testing.ClientArgs, global::Grpc.Testing.ClientStatus> RunClient(CallOptions options) |
||||
{ |
||||
var call = CreateCall(__Method_RunClient, options); |
||||
return Calls.AsyncDuplexStreamingCall(call); |
||||
} |
||||
} |
||||
|
||||
// creates service definition that can be registered with a server |
||||
public static ServerServiceDefinition BindService(IWorkerService serviceImpl) |
||||
{ |
||||
return ServerServiceDefinition.CreateBuilder(__ServiceName) |
||||
.AddMethod(__Method_RunServer, serviceImpl.RunServer) |
||||
.AddMethod(__Method_RunClient, serviceImpl.RunClient).Build(); |
||||
} |
||||
|
||||
// creates a new client |
||||
public static WorkerServiceClient NewClient(Channel channel) |
||||
{ |
||||
return new WorkerServiceClient(channel); |
||||
} |
||||
|
||||
} |
||||
} |
||||
#endregion |
@ -0,0 +1,614 @@ |
||||
// Generated by the protocol buffer compiler. DO NOT EDIT! |
||||
// source: test/proto/benchmarks/stats.proto |
||||
#pragma warning disable 1591, 0612, 3021 |
||||
#region Designer generated code |
||||
|
||||
using pb = global::Google.Protobuf; |
||||
using pbc = global::Google.Protobuf.Collections; |
||||
using pbr = global::Google.Protobuf.Reflection; |
||||
using scg = global::System.Collections.Generic; |
||||
namespace Grpc.Testing { |
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()] |
||||
public static partial class Stats { |
||||
|
||||
#region Descriptor |
||||
public static pbr::FileDescriptor Descriptor { |
||||
get { return descriptor; } |
||||
} |
||||
private static pbr::FileDescriptor descriptor; |
||||
|
||||
static Stats() { |
||||
byte[] descriptorData = global::System.Convert.FromBase64String( |
||||
string.Concat( |
||||
"CiF0ZXN0L3Byb3RvL2JlbmNobWFya3Mvc3RhdHMucHJvdG8SDGdycGMudGVz", |
||||
"dGluZyJLCgtTZXJ2ZXJTdGF0cxIUCgx0aW1lX2VsYXBzZWQYASABKAESEQoJ", |
||||
"dGltZV91c2VyGAIgASgBEhMKC3RpbWVfc3lzdGVtGAMgASgBIncKDUhpc3Rv", |
||||
"Z3JhbURhdGESDgoGYnVja2V0GAEgAygNEhAKCG1pbl9zZWVuGAIgASgBEhAK", |
||||
"CG1heF9zZWVuGAMgASgBEgsKA3N1bRgEIAEoARIWCg5zdW1fb2Zfc3F1YXJl", |
||||
"cxgFIAEoARINCgVjb3VudBgGIAEoASJ7CgtDbGllbnRTdGF0cxIuCglsYXRl", |
||||
"bmNpZXMYASABKAsyGy5ncnBjLnRlc3RpbmcuSGlzdG9ncmFtRGF0YRIUCgx0", |
||||
"aW1lX2VsYXBzZWQYAiABKAESEQoJdGltZV91c2VyGAMgASgBEhMKC3RpbWVf", |
||||
"c3lzdGVtGAQgASgBYgZwcm90bzM=")); |
||||
descriptor = pbr::FileDescriptor.InternalBuildGeneratedFileFrom(descriptorData, |
||||
new pbr::FileDescriptor[] { }, |
||||
new pbr::GeneratedCodeInfo(null, new pbr::GeneratedCodeInfo[] { |
||||
new pbr::GeneratedCodeInfo(typeof(global::Grpc.Testing.ServerStats), new[]{ "TimeElapsed", "TimeUser", "TimeSystem" }, null, null, null), |
||||
new pbr::GeneratedCodeInfo(typeof(global::Grpc.Testing.HistogramData), new[]{ "Bucket", "MinSeen", "MaxSeen", "Sum", "SumOfSquares", "Count" }, null, null, null), |
||||
new pbr::GeneratedCodeInfo(typeof(global::Grpc.Testing.ClientStats), new[]{ "Latencies", "TimeElapsed", "TimeUser", "TimeSystem" }, null, null, null) |
||||
})); |
||||
} |
||||
#endregion |
||||
|
||||
} |
||||
#region Messages |
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()] |
||||
public sealed partial class ServerStats : pb::IMessage<ServerStats> { |
||||
private static readonly pb::MessageParser<ServerStats> _parser = new pb::MessageParser<ServerStats>(() => new ServerStats()); |
||||
public static pb::MessageParser<ServerStats> Parser { get { return _parser; } } |
||||
|
||||
public static pbr::MessageDescriptor Descriptor { |
||||
get { return global::Grpc.Testing.Stats.Descriptor.MessageTypes[0]; } |
||||
} |
||||
|
||||
pbr::MessageDescriptor pb::IMessage.Descriptor { |
||||
get { return Descriptor; } |
||||
} |
||||
|
||||
public ServerStats() { |
||||
OnConstruction(); |
||||
} |
||||
|
||||
partial void OnConstruction(); |
||||
|
||||
public ServerStats(ServerStats other) : this() { |
||||
timeElapsed_ = other.timeElapsed_; |
||||
timeUser_ = other.timeUser_; |
||||
timeSystem_ = other.timeSystem_; |
||||
} |
||||
|
||||
public ServerStats Clone() { |
||||
return new ServerStats(this); |
||||
} |
||||
|
||||
public const int TimeElapsedFieldNumber = 1; |
||||
private double timeElapsed_; |
||||
public double TimeElapsed { |
||||
get { return timeElapsed_; } |
||||
set { |
||||
timeElapsed_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int TimeUserFieldNumber = 2; |
||||
private double timeUser_; |
||||
public double TimeUser { |
||||
get { return timeUser_; } |
||||
set { |
||||
timeUser_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int TimeSystemFieldNumber = 3; |
||||
private double timeSystem_; |
||||
public double TimeSystem { |
||||
get { return timeSystem_; } |
||||
set { |
||||
timeSystem_ = value; |
||||
} |
||||
} |
||||
|
||||
public override bool Equals(object other) { |
||||
return Equals(other as ServerStats); |
||||
} |
||||
|
||||
public bool Equals(ServerStats other) { |
||||
if (ReferenceEquals(other, null)) { |
||||
return false; |
||||
} |
||||
if (ReferenceEquals(other, this)) { |
||||
return true; |
||||
} |
||||
if (TimeElapsed != other.TimeElapsed) return false; |
||||
if (TimeUser != other.TimeUser) return false; |
||||
if (TimeSystem != other.TimeSystem) return false; |
||||
return true; |
||||
} |
||||
|
||||
public override int GetHashCode() { |
||||
int hash = 1; |
||||
if (TimeElapsed != 0D) hash ^= TimeElapsed.GetHashCode(); |
||||
if (TimeUser != 0D) hash ^= TimeUser.GetHashCode(); |
||||
if (TimeSystem != 0D) hash ^= TimeSystem.GetHashCode(); |
||||
return hash; |
||||
} |
||||
|
||||
public override string ToString() { |
||||
return pb::JsonFormatter.Default.Format(this); |
||||
} |
||||
|
||||
public void WriteTo(pb::CodedOutputStream output) { |
||||
if (TimeElapsed != 0D) { |
||||
output.WriteRawTag(9); |
||||
output.WriteDouble(TimeElapsed); |
||||
} |
||||
if (TimeUser != 0D) { |
||||
output.WriteRawTag(17); |
||||
output.WriteDouble(TimeUser); |
||||
} |
||||
if (TimeSystem != 0D) { |
||||
output.WriteRawTag(25); |
||||
output.WriteDouble(TimeSystem); |
||||
} |
||||
} |
||||
|
||||
public int CalculateSize() { |
||||
int size = 0; |
||||
if (TimeElapsed != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
if (TimeUser != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
if (TimeSystem != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
return size; |
||||
} |
||||
|
||||
public void MergeFrom(ServerStats other) { |
||||
if (other == null) { |
||||
return; |
||||
} |
||||
if (other.TimeElapsed != 0D) { |
||||
TimeElapsed = other.TimeElapsed; |
||||
} |
||||
if (other.TimeUser != 0D) { |
||||
TimeUser = other.TimeUser; |
||||
} |
||||
if (other.TimeSystem != 0D) { |
||||
TimeSystem = other.TimeSystem; |
||||
} |
||||
} |
||||
|
||||
public void MergeFrom(pb::CodedInputStream input) { |
||||
uint tag; |
||||
while ((tag = input.ReadTag()) != 0) { |
||||
switch(tag) { |
||||
default: |
||||
input.SkipLastField(); |
||||
break; |
||||
case 9: { |
||||
TimeElapsed = input.ReadDouble(); |
||||
break; |
||||
} |
||||
case 17: { |
||||
TimeUser = input.ReadDouble(); |
||||
break; |
||||
} |
||||
case 25: { |
||||
TimeSystem = input.ReadDouble(); |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
} |
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()] |
||||
public sealed partial class HistogramData : pb::IMessage<HistogramData> { |
||||
private static readonly pb::MessageParser<HistogramData> _parser = new pb::MessageParser<HistogramData>(() => new HistogramData()); |
||||
public static pb::MessageParser<HistogramData> Parser { get { return _parser; } } |
||||
|
||||
public static pbr::MessageDescriptor Descriptor { |
||||
get { return global::Grpc.Testing.Stats.Descriptor.MessageTypes[1]; } |
||||
} |
||||
|
||||
pbr::MessageDescriptor pb::IMessage.Descriptor { |
||||
get { return Descriptor; } |
||||
} |
||||
|
||||
public HistogramData() { |
||||
OnConstruction(); |
||||
} |
||||
|
||||
partial void OnConstruction(); |
||||
|
||||
public HistogramData(HistogramData other) : this() { |
||||
bucket_ = other.bucket_.Clone(); |
||||
minSeen_ = other.minSeen_; |
||||
maxSeen_ = other.maxSeen_; |
||||
sum_ = other.sum_; |
||||
sumOfSquares_ = other.sumOfSquares_; |
||||
count_ = other.count_; |
||||
} |
||||
|
||||
public HistogramData Clone() { |
||||
return new HistogramData(this); |
||||
} |
||||
|
||||
public const int BucketFieldNumber = 1; |
||||
private static readonly pb::FieldCodec<uint> _repeated_bucket_codec |
||||
= pb::FieldCodec.ForUInt32(10); |
||||
private readonly pbc::RepeatedField<uint> bucket_ = new pbc::RepeatedField<uint>(); |
||||
public pbc::RepeatedField<uint> Bucket { |
||||
get { return bucket_; } |
||||
} |
||||
|
||||
public const int MinSeenFieldNumber = 2; |
||||
private double minSeen_; |
||||
public double MinSeen { |
||||
get { return minSeen_; } |
||||
set { |
||||
minSeen_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int MaxSeenFieldNumber = 3; |
||||
private double maxSeen_; |
||||
public double MaxSeen { |
||||
get { return maxSeen_; } |
||||
set { |
||||
maxSeen_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int SumFieldNumber = 4; |
||||
private double sum_; |
||||
public double Sum { |
||||
get { return sum_; } |
||||
set { |
||||
sum_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int SumOfSquaresFieldNumber = 5; |
||||
private double sumOfSquares_; |
||||
public double SumOfSquares { |
||||
get { return sumOfSquares_; } |
||||
set { |
||||
sumOfSquares_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int CountFieldNumber = 6; |
||||
private double count_; |
||||
public double Count { |
||||
get { return count_; } |
||||
set { |
||||
count_ = value; |
||||
} |
||||
} |
||||
|
||||
public override bool Equals(object other) { |
||||
return Equals(other as HistogramData); |
||||
} |
||||
|
||||
public bool Equals(HistogramData other) { |
||||
if (ReferenceEquals(other, null)) { |
||||
return false; |
||||
} |
||||
if (ReferenceEquals(other, this)) { |
||||
return true; |
||||
} |
||||
if(!bucket_.Equals(other.bucket_)) return false; |
||||
if (MinSeen != other.MinSeen) return false; |
||||
if (MaxSeen != other.MaxSeen) return false; |
||||
if (Sum != other.Sum) return false; |
||||
if (SumOfSquares != other.SumOfSquares) return false; |
||||
if (Count != other.Count) return false; |
||||
return true; |
||||
} |
||||
|
||||
public override int GetHashCode() { |
||||
int hash = 1; |
||||
hash ^= bucket_.GetHashCode(); |
||||
if (MinSeen != 0D) hash ^= MinSeen.GetHashCode(); |
||||
if (MaxSeen != 0D) hash ^= MaxSeen.GetHashCode(); |
||||
if (Sum != 0D) hash ^= Sum.GetHashCode(); |
||||
if (SumOfSquares != 0D) hash ^= SumOfSquares.GetHashCode(); |
||||
if (Count != 0D) hash ^= Count.GetHashCode(); |
||||
return hash; |
||||
} |
||||
|
||||
public override string ToString() { |
||||
return pb::JsonFormatter.Default.Format(this); |
||||
} |
||||
|
||||
public void WriteTo(pb::CodedOutputStream output) { |
||||
bucket_.WriteTo(output, _repeated_bucket_codec); |
||||
if (MinSeen != 0D) { |
||||
output.WriteRawTag(17); |
||||
output.WriteDouble(MinSeen); |
||||
} |
||||
if (MaxSeen != 0D) { |
||||
output.WriteRawTag(25); |
||||
output.WriteDouble(MaxSeen); |
||||
} |
||||
if (Sum != 0D) { |
||||
output.WriteRawTag(33); |
||||
output.WriteDouble(Sum); |
||||
} |
||||
if (SumOfSquares != 0D) { |
||||
output.WriteRawTag(41); |
||||
output.WriteDouble(SumOfSquares); |
||||
} |
||||
if (Count != 0D) { |
||||
output.WriteRawTag(49); |
||||
output.WriteDouble(Count); |
||||
} |
||||
} |
||||
|
||||
public int CalculateSize() { |
||||
int size = 0; |
||||
size += bucket_.CalculateSize(_repeated_bucket_codec); |
||||
if (MinSeen != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
if (MaxSeen != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
if (Sum != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
if (SumOfSquares != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
if (Count != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
return size; |
||||
} |
||||
|
||||
public void MergeFrom(HistogramData other) { |
||||
if (other == null) { |
||||
return; |
||||
} |
||||
bucket_.Add(other.bucket_); |
||||
if (other.MinSeen != 0D) { |
||||
MinSeen = other.MinSeen; |
||||
} |
||||
if (other.MaxSeen != 0D) { |
||||
MaxSeen = other.MaxSeen; |
||||
} |
||||
if (other.Sum != 0D) { |
||||
Sum = other.Sum; |
||||
} |
||||
if (other.SumOfSquares != 0D) { |
||||
SumOfSquares = other.SumOfSquares; |
||||
} |
||||
if (other.Count != 0D) { |
||||
Count = other.Count; |
||||
} |
||||
} |
||||
|
||||
public void MergeFrom(pb::CodedInputStream input) { |
||||
uint tag; |
||||
while ((tag = input.ReadTag()) != 0) { |
||||
switch(tag) { |
||||
default: |
||||
input.SkipLastField(); |
||||
break; |
||||
case 10: |
||||
case 8: { |
||||
bucket_.AddEntriesFrom(input, _repeated_bucket_codec); |
||||
break; |
||||
} |
||||
case 17: { |
||||
MinSeen = input.ReadDouble(); |
||||
break; |
||||
} |
||||
case 25: { |
||||
MaxSeen = input.ReadDouble(); |
||||
break; |
||||
} |
||||
case 33: { |
||||
Sum = input.ReadDouble(); |
||||
break; |
||||
} |
||||
case 41: { |
||||
SumOfSquares = input.ReadDouble(); |
||||
break; |
||||
} |
||||
case 49: { |
||||
Count = input.ReadDouble(); |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
} |
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()] |
||||
public sealed partial class ClientStats : pb::IMessage<ClientStats> { |
||||
private static readonly pb::MessageParser<ClientStats> _parser = new pb::MessageParser<ClientStats>(() => new ClientStats()); |
||||
public static pb::MessageParser<ClientStats> Parser { get { return _parser; } } |
||||
|
||||
public static pbr::MessageDescriptor Descriptor { |
||||
get { return global::Grpc.Testing.Stats.Descriptor.MessageTypes[2]; } |
||||
} |
||||
|
||||
pbr::MessageDescriptor pb::IMessage.Descriptor { |
||||
get { return Descriptor; } |
||||
} |
||||
|
||||
public ClientStats() { |
||||
OnConstruction(); |
||||
} |
||||
|
||||
partial void OnConstruction(); |
||||
|
||||
public ClientStats(ClientStats other) : this() { |
||||
Latencies = other.latencies_ != null ? other.Latencies.Clone() : null; |
||||
timeElapsed_ = other.timeElapsed_; |
||||
timeUser_ = other.timeUser_; |
||||
timeSystem_ = other.timeSystem_; |
||||
} |
||||
|
||||
public ClientStats Clone() { |
||||
return new ClientStats(this); |
||||
} |
||||
|
||||
public const int LatenciesFieldNumber = 1; |
||||
private global::Grpc.Testing.HistogramData latencies_; |
||||
public global::Grpc.Testing.HistogramData Latencies { |
||||
get { return latencies_; } |
||||
set { |
||||
latencies_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int TimeElapsedFieldNumber = 2; |
||||
private double timeElapsed_; |
||||
public double TimeElapsed { |
||||
get { return timeElapsed_; } |
||||
set { |
||||
timeElapsed_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int TimeUserFieldNumber = 3; |
||||
private double timeUser_; |
||||
public double TimeUser { |
||||
get { return timeUser_; } |
||||
set { |
||||
timeUser_ = value; |
||||
} |
||||
} |
||||
|
||||
public const int TimeSystemFieldNumber = 4; |
||||
private double timeSystem_; |
||||
public double TimeSystem { |
||||
get { return timeSystem_; } |
||||
set { |
||||
timeSystem_ = value; |
||||
} |
||||
} |
||||
|
||||
public override bool Equals(object other) { |
||||
return Equals(other as ClientStats); |
||||
} |
||||
|
||||
public bool Equals(ClientStats other) { |
||||
if (ReferenceEquals(other, null)) { |
||||
return false; |
||||
} |
||||
if (ReferenceEquals(other, this)) { |
||||
return true; |
||||
} |
||||
if (!object.Equals(Latencies, other.Latencies)) return false; |
||||
if (TimeElapsed != other.TimeElapsed) return false; |
||||
if (TimeUser != other.TimeUser) return false; |
||||
if (TimeSystem != other.TimeSystem) return false; |
||||
return true; |
||||
} |
||||
|
||||
public override int GetHashCode() { |
||||
int hash = 1; |
||||
if (latencies_ != null) hash ^= Latencies.GetHashCode(); |
||||
if (TimeElapsed != 0D) hash ^= TimeElapsed.GetHashCode(); |
||||
if (TimeUser != 0D) hash ^= TimeUser.GetHashCode(); |
||||
if (TimeSystem != 0D) hash ^= TimeSystem.GetHashCode(); |
||||
return hash; |
||||
} |
||||
|
||||
public override string ToString() { |
||||
return pb::JsonFormatter.Default.Format(this); |
||||
} |
||||
|
||||
public void WriteTo(pb::CodedOutputStream output) { |
||||
if (latencies_ != null) { |
||||
output.WriteRawTag(10); |
||||
output.WriteMessage(Latencies); |
||||
} |
||||
if (TimeElapsed != 0D) { |
||||
output.WriteRawTag(17); |
||||
output.WriteDouble(TimeElapsed); |
||||
} |
||||
if (TimeUser != 0D) { |
||||
output.WriteRawTag(25); |
||||
output.WriteDouble(TimeUser); |
||||
} |
||||
if (TimeSystem != 0D) { |
||||
output.WriteRawTag(33); |
||||
output.WriteDouble(TimeSystem); |
||||
} |
||||
} |
||||
|
||||
public int CalculateSize() { |
||||
int size = 0; |
||||
if (latencies_ != null) { |
||||
size += 1 + pb::CodedOutputStream.ComputeMessageSize(Latencies); |
||||
} |
||||
if (TimeElapsed != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
if (TimeUser != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
if (TimeSystem != 0D) { |
||||
size += 1 + 8; |
||||
} |
||||
return size; |
||||
} |
||||
|
||||
public void MergeFrom(ClientStats other) { |
||||
if (other == null) { |
||||
return; |
||||
} |
||||
if (other.latencies_ != null) { |
||||
if (latencies_ == null) { |
||||
latencies_ = new global::Grpc.Testing.HistogramData(); |
||||
} |
||||
Latencies.MergeFrom(other.Latencies); |
||||
} |
||||
if (other.TimeElapsed != 0D) { |
||||
TimeElapsed = other.TimeElapsed; |
||||
} |
||||
if (other.TimeUser != 0D) { |
||||
TimeUser = other.TimeUser; |
||||
} |
||||
if (other.TimeSystem != 0D) { |
||||
TimeSystem = other.TimeSystem; |
||||
} |
||||
} |
||||
|
||||
public void MergeFrom(pb::CodedInputStream input) { |
||||
uint tag; |
||||
while ((tag = input.ReadTag()) != 0) { |
||||
switch(tag) { |
||||
default: |
||||
input.SkipLastField(); |
||||
break; |
||||
case 10: { |
||||
if (latencies_ == null) { |
||||
latencies_ = new global::Grpc.Testing.HistogramData(); |
||||
} |
||||
input.ReadMessage(latencies_); |
||||
break; |
||||
} |
||||
case 17: { |
||||
TimeElapsed = input.ReadDouble(); |
||||
break; |
||||
} |
||||
case 25: { |
||||
TimeUser = input.ReadDouble(); |
||||
break; |
||||
} |
||||
case 33: { |
||||
TimeSystem = input.ReadDouble(); |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
} |
||||
|
||||
#endregion |
||||
|
||||
} |
||||
|
||||
#endregion Designer generated code |
@ -0,0 +1,78 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.Diagnostics; |
||||
using System.IO; |
||||
using System.Linq; |
||||
using System.Text.RegularExpressions; |
||||
using System.Threading; |
||||
using System.Threading.Tasks; |
||||
using Google.Protobuf; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
using NUnit.Framework; |
||||
using Grpc.Testing; |
||||
|
||||
namespace Grpc.IntegrationTesting |
||||
{ |
||||
/// <summary> |
||||
/// Snapshottable wall clock stopwatch. |
||||
/// </summary> |
||||
public class WallClockStopwatch |
||||
{ |
||||
long startTicks; |
||||
|
||||
public WallClockStopwatch() |
||||
{ |
||||
this.startTicks = DateTime.UtcNow.Ticks; |
||||
} |
||||
|
||||
public TimeSpan GetElapsedSnapshot(bool reset) |
||||
{ |
||||
var utcNow = DateTime.UtcNow; |
||||
|
||||
long oldStartTicks; |
||||
if (reset) |
||||
{ |
||||
oldStartTicks = Interlocked.Exchange(ref this.startTicks, utcNow.Ticks); |
||||
} |
||||
else |
||||
{ |
||||
oldStartTicks = this.startTicks; |
||||
} |
||||
return utcNow - new DateTime(oldStartTicks, DateTimeKind.Utc); |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,96 @@ |
||||
#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 System.Collections.Generic; |
||||
using System.Threading; |
||||
using System.Threading.Tasks; |
||||
using Google.Protobuf; |
||||
using Grpc.Core; |
||||
using Grpc.Core.Utils; |
||||
using Grpc.IntegrationTesting; |
||||
|
||||
namespace Grpc.Testing |
||||
{ |
||||
/// <summary> |
||||
/// Implementation of WorkerService server |
||||
/// </summary> |
||||
public class WorkerServiceImpl : WorkerService.IWorkerService |
||||
{ |
||||
public async Task RunServer(IAsyncStreamReader<ServerArgs> requestStream, IServerStreamWriter<ServerStatus> responseStream, ServerCallContext context) |
||||
{ |
||||
Grpc.Core.Utils.Preconditions.CheckState(await requestStream.MoveNext()); |
||||
var serverConfig = requestStream.Current.Setup; |
||||
var runner = ServerRunners.CreateStarted(serverConfig); |
||||
|
||||
await responseStream.WriteAsync(new ServerStatus |
||||
{ |
||||
Stats = runner.GetStats(false), |
||||
Port = runner.BoundPort, |
||||
Cores = 0, // TODO: set number of cores |
||||
}); |
||||
|
||||
while (await requestStream.MoveNext()) |
||||
{ |
||||
var reset = requestStream.Current.Mark.Reset; |
||||
await responseStream.WriteAsync(new ServerStatus |
||||
{ |
||||
Stats = runner.GetStats(reset) |
||||
}); |
||||
} |
||||
await runner.StopAsync(); |
||||
} |
||||
|
||||
public async Task RunClient(IAsyncStreamReader<ClientArgs> requestStream, IServerStreamWriter<ClientStatus> responseStream, ServerCallContext context) |
||||
{ |
||||
Grpc.Core.Utils.Preconditions.CheckState(await requestStream.MoveNext()); |
||||
var clientConfig = requestStream.Current.Setup; |
||||
var runner = ClientRunners.CreateStarted(clientConfig); |
||||
|
||||
await responseStream.WriteAsync(new ClientStatus |
||||
{ |
||||
Stats = runner.GetStats(false) |
||||
}); |
||||
|
||||
while (await requestStream.MoveNext()) |
||||
{ |
||||
var reset = requestStream.Current.Mark.Reset; |
||||
await responseStream.WriteAsync(new ClientStatus |
||||
{ |
||||
Stats = runner.GetStats(reset) |
||||
}); |
||||
} |
||||
await runner.StopAsync(); |
||||
} |
||||
} |
||||
} |
Loading…
Reference in new issue