Skip to content
Snippets Groups Projects
Commit 34236d5b authored by Craig Tiller's avatar Craig Tiller
Browse files

Merge github.com:grpc/grpc into fuzzy-bits

parents 56486054 6e6230a6
No related branches found
No related tags found
No related merge requests found
Showing
with 1268 additions and 620 deletions
#region Copyright notice and license
// Copyright 2015, Google Inc.
// Copyright 2015-2016, Google Inc.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
......@@ -46,16 +46,13 @@ namespace Grpc.Testing
/// </summary>
public class BenchmarkServiceImpl : BenchmarkService.IBenchmarkService
{
private readonly int responseSize;
public BenchmarkServiceImpl(int responseSize)
public BenchmarkServiceImpl()
{
this.responseSize = responseSize;
}
public Task<SimpleResponse> UnaryCall(SimpleRequest request, ServerCallContext context)
{
var response = new SimpleResponse { Payload = CreateZerosPayload(responseSize) };
var response = new SimpleResponse { Payload = CreateZerosPayload(request.ResponseSize) };
return Task.FromResult(response);
}
......@@ -63,7 +60,7 @@ namespace Grpc.Testing
{
await requestStream.ForEachAsync(async request =>
{
var response = new SimpleResponse { Payload = CreateZerosPayload(responseSize) };
var response = new SimpleResponse { Payload = CreateZerosPayload(request.ResponseSize) };
await responseStream.WriteAsync(response);
});
}
......
......@@ -41,6 +41,7 @@ using System.Threading;
using System.Threading.Tasks;
using Google.Protobuf;
using Grpc.Core;
using Grpc.Core.Logging;
using Grpc.Core.Utils;
using NUnit.Framework;
using Grpc.Testing;
......@@ -50,42 +51,65 @@ namespace Grpc.IntegrationTesting
/// <summary>
/// Helper methods to start client runners for performance testing.
/// </summary>
public static class ClientRunners
public class ClientRunners
{
static readonly ILogger Logger = GrpcEnvironment.Logger.ForType<ClientRunners>();
/// <summary>
/// Creates a started client runner.
/// </summary>
public static IClientRunner CreateStarted(ClientConfig config)
{
Logger.Debug("ClientConfig: {0}", config);
string target = config.ServerTargets.Single();
GrpcPreconditions.CheckArgument(config.LoadParams.LoadCase == LoadParams.LoadOneofCase.ClosedLoop);
GrpcPreconditions.CheckArgument(config.LoadParams.LoadCase == LoadParams.LoadOneofCase.ClosedLoop,
"Only closed loop scenario supported for C#");
GrpcPreconditions.CheckArgument(config.ClientChannels == 1, "ClientConfig.ClientChannels needs to be 1");
var credentials = config.SecurityParams != null ? TestCredentials.CreateSslCredentials() : ChannelCredentials.Insecure;
var channel = new Channel(target, credentials);
if (config.OutstandingRpcsPerChannel != 0)
{
Logger.Warning("ClientConfig.OutstandingRpcsPerChannel is not supported for C#. Ignoring the value");
}
if (config.AsyncClientThreads != 0)
{
Logger.Warning("ClientConfig.AsyncClientThreads is not supported for C#. Ignoring the value");
}
if (config.CoreLimit != 0)
{
Logger.Warning("ClientConfig.CoreLimit is not supported for C#. Ignoring the value");
}
if (config.CoreList.Count > 0)
{
Logger.Warning("ClientConfig.CoreList is not supported for C#. Ignoring the value");
}
switch (config.RpcType)
var credentials = config.SecurityParams != null ? TestCredentials.CreateSslCredentials() : ChannelCredentials.Insecure;
List<ChannelOption> channelOptions = null;
if (config.SecurityParams != null && config.SecurityParams.ServerHostOverride != "")
{
case RpcType.UNARY:
return new SyncUnaryClientRunner(channel,
config.PayloadConfig.SimpleParams.ReqSize,
config.HistogramParams);
case RpcType.STREAMING:
default:
throw new ArgumentException("Unsupported RpcType.");
channelOptions = new List<ChannelOption>
{
new ChannelOption(ChannelOptions.SslTargetNameOverride, config.SecurityParams.ServerHostOverride)
};
}
var channel = new Channel(target, credentials, channelOptions);
return new ClientRunnerImpl(channel,
config.ClientType,
config.RpcType,
config.PayloadConfig,
config.HistogramParams);
}
}
/// <summary>
/// Client that starts synchronous unary calls in a closed loop.
/// </summary>
public class SyncUnaryClientRunner : IClientRunner
public class ClientRunnerImpl : IClientRunner
{
const double SecondsToNanos = 1e9;
readonly Channel channel;
readonly int payloadSize;
readonly ClientType clientType;
readonly RpcType rpcType;
readonly PayloadConfig payloadConfig;
readonly Histogram histogram;
readonly BenchmarkService.IBenchmarkServiceClient client;
......@@ -93,15 +117,19 @@ namespace Grpc.IntegrationTesting
readonly CancellationTokenSource stoppedCts;
readonly WallClockStopwatch wallClockStopwatch = new WallClockStopwatch();
public SyncUnaryClientRunner(Channel channel, int payloadSize, HistogramParams histogramParams)
public ClientRunnerImpl(Channel channel, ClientType clientType, RpcType rpcType, PayloadConfig payloadConfig, HistogramParams histogramParams)
{
this.channel = GrpcPreconditions.CheckNotNull(channel);
this.payloadSize = payloadSize;
this.clientType = clientType;
this.rpcType = rpcType;
this.payloadConfig = payloadConfig;
this.histogram = new Histogram(histogramParams.Resolution, histogramParams.MaxPossible);
this.stoppedCts = new CancellationTokenSource();
this.client = BenchmarkService.NewClient(channel);
this.runnerTask = Task.Factory.StartNew(Run, TaskCreationOptions.LongRunning);
var threadBody = GetThreadBody();
this.runnerTask = Task.Factory.StartNew(threadBody, TaskCreationOptions.LongRunning);
}
public ClientStats GetStats(bool reset)
......@@ -126,12 +154,9 @@ namespace Grpc.IntegrationTesting
await channel.ShutdownAsync();
}
private void Run()
private void RunClosedLoopUnary()
{
var request = new SimpleRequest
{
Payload = CreateZerosPayload(payloadSize)
};
var request = CreateSimpleRequest();
var stopwatch = new Stopwatch();
while (!stoppedCts.Token.IsCancellationRequested)
......@@ -145,6 +170,124 @@ namespace Grpc.IntegrationTesting
}
}
private async Task RunClosedLoopUnaryAsync()
{
var request = CreateSimpleRequest();
var stopwatch = new Stopwatch();
while (!stoppedCts.Token.IsCancellationRequested)
{
stopwatch.Restart();
await client.UnaryCallAsync(request);
stopwatch.Stop();
// spec requires data point in nanoseconds.
histogram.AddObservation(stopwatch.Elapsed.TotalSeconds * SecondsToNanos);
}
}
private async Task RunClosedLoopStreamingAsync()
{
var request = CreateSimpleRequest();
var stopwatch = new Stopwatch();
using (var call = client.StreamingCall())
{
while (!stoppedCts.Token.IsCancellationRequested)
{
stopwatch.Restart();
await call.RequestStream.WriteAsync(request);
await call.ResponseStream.MoveNext();
stopwatch.Stop();
// spec requires data point in nanoseconds.
histogram.AddObservation(stopwatch.Elapsed.TotalSeconds * SecondsToNanos);
}
// finish the streaming call
await call.RequestStream.CompleteAsync();
Assert.IsFalse(await call.ResponseStream.MoveNext());
}
}
private async Task RunGenericClosedLoopStreamingAsync()
{
var request = CreateByteBufferRequest();
var stopwatch = new Stopwatch();
var callDetails = new CallInvocationDetails<byte[], byte[]>(channel, GenericService.StreamingCallMethod, new CallOptions());
using (var call = Calls.AsyncDuplexStreamingCall(callDetails))
{
while (!stoppedCts.Token.IsCancellationRequested)
{
stopwatch.Restart();
await call.RequestStream.WriteAsync(request);
await call.ResponseStream.MoveNext();
stopwatch.Stop();
// spec requires data point in nanoseconds.
histogram.AddObservation(stopwatch.Elapsed.TotalSeconds * SecondsToNanos);
}
// finish the streaming call
await call.RequestStream.CompleteAsync();
Assert.IsFalse(await call.ResponseStream.MoveNext());
}
}
private Action GetThreadBody()
{
if (payloadConfig.PayloadCase == PayloadConfig.PayloadOneofCase.BytebufParams)
{
GrpcPreconditions.CheckArgument(clientType == ClientType.ASYNC_CLIENT, "Generic client only supports async API");
GrpcPreconditions.CheckArgument(rpcType == RpcType.STREAMING, "Generic client only supports streaming calls");
return () =>
{
RunGenericClosedLoopStreamingAsync().Wait();
};
}
GrpcPreconditions.CheckNotNull(payloadConfig.SimpleParams);
if (clientType == ClientType.SYNC_CLIENT)
{
GrpcPreconditions.CheckArgument(rpcType == RpcType.UNARY, "Sync client can only be used for Unary calls in C#");
return RunClosedLoopUnary;
}
else if (clientType == ClientType.ASYNC_CLIENT)
{
switch (rpcType)
{
case RpcType.UNARY:
return () =>
{
RunClosedLoopUnaryAsync().Wait();
};
case RpcType.STREAMING:
return () =>
{
RunClosedLoopStreamingAsync().Wait();
};
}
}
throw new ArgumentException("Unsupported configuration.");
}
private SimpleRequest CreateSimpleRequest()
{
GrpcPreconditions.CheckNotNull(payloadConfig.SimpleParams);
return new SimpleRequest
{
Payload = CreateZerosPayload(payloadConfig.SimpleParams.ReqSize),
ResponseSize = payloadConfig.SimpleParams.RespSize
};
}
private byte[] CreateByteBufferRequest()
{
return new byte[payloadConfig.BytebufParams.ReqSize];
}
private static Payload CreateZerosPayload(int size)
{
return new Payload { Body = ByteString.CopyFrom(new byte[size]) };
......
#region Copyright notice and license
// Copyright 2016, 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>
/// Utility methods for defining and calling a service that doesn't use protobufs
/// for serialization/deserialization.
/// </summary>
public static class GenericService
{
readonly static Marshaller<byte[]> ByteArrayMarshaller = new Marshaller<byte[]>((b) => b, (b) => b);
public readonly static Method<byte[], byte[]> StreamingCallMethod = new Method<byte[], byte[]>(
MethodType.DuplexStreaming,
"grpc.testing.BenchmarkService",
"StreamingCall",
ByteArrayMarshaller,
ByteArrayMarshaller
);
public static ServerServiceDefinition BindHandler(DuplexStreamingServerMethod<byte[], byte[]> handler)
{
return ServerServiceDefinition.CreateBuilder(StreamingCallMethod.ServiceName)
.AddMethod(StreamingCallMethod, handler).Build();
}
}
}
......@@ -120,6 +120,7 @@
<Compile Include="WorkerServiceImpl.cs" />
<Compile Include="QpsWorker.cs" />
<Compile Include="WallClockStopwatch.cs" />
<Compile Include="GenericService.cs" />
</ItemGroup>
<Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" />
<ItemGroup>
......
......@@ -55,14 +55,7 @@ namespace Grpc.IntegrationTesting
{
var serverConfig = new ServerConfig
{
ServerType = ServerType.ASYNC_SERVER,
PayloadConfig = new PayloadConfig
{
SimpleParams = new SimpleProtoParams
{
RespSize = 100
}
}
ServerType = ServerType.ASYNC_SERVER
};
serverRunner = ServerRunners.CreateStarted(serverConfig);
}
......@@ -88,7 +81,8 @@ namespace Grpc.IntegrationTesting
{
SimpleParams = new SimpleProtoParams
{
ReqSize = 100
ReqSize = 100,
RespSize = 100
}
},
HistogramParams = new HistogramParams
......
......@@ -41,6 +41,7 @@ using System.Threading;
using System.Threading.Tasks;
using Google.Protobuf;
using Grpc.Core;
using Grpc.Core.Logging;
using Grpc.Core.Utils;
using NUnit.Framework;
using Grpc.Testing;
......@@ -50,27 +51,78 @@ namespace Grpc.IntegrationTesting
/// <summary>
/// Helper methods to start server runners for performance testing.
/// </summary>
public static class ServerRunners
public class ServerRunners
{
static readonly ILogger Logger = GrpcEnvironment.Logger.ForType<ServerRunners>();
/// <summary>
/// Creates a started server runner.
/// </summary>
public static IServerRunner CreateStarted(ServerConfig config)
{
GrpcPreconditions.CheckArgument(config.ServerType == ServerType.ASYNC_SERVER);
Logger.Debug("ServerConfig: {0}", config);
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;
if (config.AsyncServerThreads != 0)
{
Logger.Warning("ServerConfig.AsyncServerThreads is not supported for C#. Ignoring the value");
}
if (config.CoreLimit != 0)
{
Logger.Warning("ServerConfig.CoreLimit is not supported for C#. Ignoring the value");
}
if (config.CoreList.Count > 0)
{
Logger.Warning("ServerConfig.CoreList is not supported for C#. Ignoring the value");
}
ServerServiceDefinition service = null;
if (config.ServerType == ServerType.ASYNC_SERVER)
{
GrpcPreconditions.CheckArgument(config.PayloadConfig == null,
"ServerConfig.PayloadConfig shouldn't be set for BenchmarkService based server.");
service = BenchmarkService.BindService(new BenchmarkServiceImpl());
}
else if (config.ServerType == ServerType.ASYNC_GENERIC_SERVER)
{
var genericService = new GenericServiceImpl(config.PayloadConfig.BytebufParams.RespSize);
service = GenericService.BindHandler(genericService.StreamingCall);
}
else
{
throw new ArgumentException("Unsupported ServerType");
}
var server = new Server
{
Services = { BenchmarkService.BindService(new BenchmarkServiceImpl(responseSize)) },
Services = { service },
Ports = { new ServerPort("[::]", config.Port, credentials) }
};
server.Start();
return new ServerRunnerImpl(server);
}
private class GenericServiceImpl
{
readonly byte[] response;
public GenericServiceImpl(int responseSize)
{
this.response = new byte[responseSize];
}
/// <summary>
/// Generic streaming call handler.
/// </summary>
public async Task StreamingCall(IAsyncStreamReader<byte[]> requestStream, IServerStreamWriter<byte[]> responseStream, ServerCallContext context)
{
await requestStream.ForEachAsync(async request =>
{
await responseStream.WriteAsync(response);
});
}
}
}
/// <summary>
......@@ -119,6 +171,5 @@ namespace Grpc.IntegrationTesting
{
return server.ShutdownAsync();
}
}
}
}
......@@ -54,7 +54,9 @@
GRPC_XMACRO_ITEM.
#endif
#if TARGET_OS_IPHONE
GRPC_XMACRO_ITEM(isCell, IsWWAN)
#endif
GRPC_XMACRO_ITEM(reachable, Reachable)
GRPC_XMACRO_ITEM(transientConnection, TransientConnection)
GRPC_XMACRO_ITEM(connectionRequired, ConnectionRequired)
......
# Google Cloud platform API libraries
RUN apt-get update && apt-get install -y python-pip && apt-get clean
RUN pip install --upgrade google-api-python-client
%YAML 1.2
--- |
# Copyright 2015-2016, 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.
FROM debian:jessie
<%include file="../apt_get_basic.include"/>
<%include file="../ccache_setup.include"/>
<%include file="../cxx_deps.include"/>
<%include file="../gcp_api_libraries.include"/>
<%include file="../clang_update.include"/>
# Define the default command.
CMD ["bash"]
......@@ -27,12 +27,9 @@
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
# A work-in-progress Dockerfile that allows running gRPC test suites
# inside a docker container.
FROM debian:jessie
# Install Git.
# Install Git and basic packages.
RUN apt-get update && apt-get install -y \
autoconf \
autotools-dev \
......@@ -43,13 +40,16 @@ RUN apt-get update && apt-get install -y \
gcc \
gcc-multilib \
git \
golang \
gyp \
lcov \
libc6 \
libc6-dbg \
libc6-dev \
libgtest-dev \
libtool \
make \
perl \
strace \
python-dev \
python-setuptools \
......@@ -59,7 +59,9 @@ RUN apt-get update && apt-get install -y \
wget \
zip && apt-get clean
RUN easy_install -U pip
#================
# Build profiling
RUN apt-get update && apt-get install -y time && apt-get clean
# Prepare ccache
RUN ln -s /usr/bin/ccache /usr/local/bin/gcc
......@@ -69,12 +71,47 @@ RUN ln -s /usr/bin/ccache /usr/local/bin/c++
RUN ln -s /usr/bin/ccache /usr/local/bin/clang
RUN ln -s /usr/bin/ccache /usr/local/bin/clang++
##################
#=================
# C++ dependencies
RUN apt-get update && apt-get -y install libgflags-dev libgtest-dev libc++-dev clang
RUN apt-get update && apt-get -y install libgflags-dev libgtest-dev libc++-dev clang && apt-get clean
# Google Cloud platform API libraries (for BigQuery)
# Google Cloud platform API libraries
RUN apt-get update && apt-get install -y python-pip && apt-get clean
RUN pip install --upgrade google-api-python-client
#=================
# Update clang to a version with improved tsan
RUN apt-get update && apt-get -y install python cmake && apt-get clean
RUN git clone -n -b release_38 http://llvm.org/git/llvm.git && \
cd llvm && git checkout ad57503 && cd ..
RUN git clone -n -b release_38 http://llvm.org/git/clang.git && \
cd clang && git checkout ad2c56e && cd ..
RUN git clone -n -b release_38 http://llvm.org/git/compiler-rt.git && \
cd compiler-rt && git checkout 3176922 && cd ..
RUN git clone -n -b release_38 \
http://llvm.org/git/clang-tools-extra.git && cd clang-tools-extra && \
git checkout c288525 && cd ..
RUN git clone -n -b release_38 http://llvm.org/git/libcxx.git && \
cd libcxx && git checkout fda3549 && cd ..
RUN git clone -n -b release_38 http://llvm.org/git/libcxxabi.git && \
cd libcxxabi && git checkout 8d4e51d && cd ..
RUN mv clang llvm/tools
RUN mv compiler-rt llvm/projects
RUN mv clang-tools-extra llvm/tools/clang/tools
RUN mv libcxx llvm/projects
RUN mv libcxxabi llvm/projects
RUN mkdir llvm-build
RUN cd llvm-build && cmake \
-DCMAKE_BUILD_TYPE:STRING=Release \
-DCMAKE_INSTALL_PREFIX:STRING=/usr \
-DLLVM_TARGETS_TO_BUILD:STRING=X86 \
../llvm
RUN make -C llvm-build && make -C llvm-build install && rm -rf llvm-build
# Define the default command.
CMD ["bash"]
......@@ -41,5 +41,7 @@ cd /var/local/git/grpc
make install-certs
BUILD_TYPE=${BUILD_TYPE:=opt}
# build C++ interop stress client, interop client and server
make stress_test metrics_client interop_client interop_server
make CONFIG=$BUILD_TYPE stress_test metrics_client interop_client interop_server
......@@ -34,10 +34,12 @@
set -x
# Params:
# INTEROP_IMAGE - name of tag of the final interop image
# INTEROP_IMAGE - Name of tag of the final interop image
# INTEROP_IMAGE_TAG - Optional. If set, the created image will be tagged using
# the command: 'docker tag $INTEROP_IMAGE $INTEROP_IMAGE_REPOSITORY_TAG'
# BASE_NAME - base name used to locate the base Dockerfile and build script
# BASE_NAME - Base name used to locate the base Dockerfile and build script
# BUILD_TYPE - The 'CONFIG' variable passed to the 'make' command (example:
# asan, tsan. Default value: opt).
# TTY_FLAG - optional -t flag to make docker allocate tty
# BUILD_INTEROP_DOCKER_EXTRA_ARGS - optional args to be passed to the
# docker run command
......@@ -71,6 +73,7 @@ CONTAINER_NAME="build_${BASE_NAME}_$(uuidgen)"
(docker run \
-e CCACHE_DIR=/tmp/ccache \
-e THIS_IS_REALLY_NEEDED='see https://github.com/docker/docker/issues/14203 for why docker is awful' \
-e BUILD_TYPE=${BUILD_TYPE:=opt} \
-i $TTY_FLAG \
$MOUNT_ARGS \
$BUILD_INTEROP_DOCKER_EXTRA_ARGS \
......
......@@ -67,8 +67,10 @@ The script has several parameters and you can find out more details by using the
- `<grpc_root_dir>$ tools/run_tests/stress_test/run_stress_tests_on_gke.py --help`
> **Example**
> `$ tools/run_tests/stress_test/run_stress_tests_on_gke.py --project_id=sree-gce --test_duration_secs=180 --num_clients=5`
> ```bash
> $ # Change to the grpc root directory
> $ cd $GRPC_ROOT
> $ tools/run_tests/stress_test/run_on_gke.py --project_id=sree-gce --config_file=tools/run_tests/stress_test/configs/opt.json
> ```
> Launches the 5 instances of stress test clients, 1 instance of stress test server and runs the test for 180 seconds. The test would be run on the default container cluster (that you have set in `gcloud`) in the project `sree-gce`.
> Note: we currently do not have the ability to launch multiple instances of the server. This can be added very easily in future
> The above runs the stress test on GKE under the project `sree-gce` in the default cluster (that you set by `gcloud` command earlier). The test settings (like number of client instances, servers, the parmeters to pass, test cases etc) are all loaded from the config file `$GRPC_ROOT/tools/run_tests/stress_test/opt.json`
{
"dockerImages": {
"grpc_stress_cxx_opt" : {
"buildScript": "tools/jenkins/build_interop_stress_image.sh",
"dockerFileDir": "grpc_interop_stress_cxx",
"buildType": "opt"
},
"grpc_stress_cxx_tsan": {
"buildScript": "tools/jenkins/build_interop_stress_image.sh",
"dockerFileDir": "grpc_interop_stress_cxx",
"buildType": "tsan"
},
"grpc_stress_cxx_asan": {
"buildScript": "tools/jenkins/build_interop_stress_image.sh",
"dockerFileDir": "grpc_interop_stress_cxx",
"buildType": "asan"
}
},
"clientTemplates": {
"baseTemplates": {
"default": {
"wrapperScriptPath": "/var/local/git/grpc/tools/gcp/stress_test/run_client.py",
"pollIntervalSecs": 60,
"clientArgs": {
"num_channels_per_server":5,
"num_stubs_per_channel":10,
"test_cases": "empty_unary:1,large_unary:1,client_streaming:1,server_streaming:1,empty_stream:1",
"metrics_port": 8081,
"metrics_collection_interval_secs":60
},
"metricsPort": 8081,
"metricsArgs": {
"metrics_server_address": "localhost:8081",
"total_only": "true"
}
}
},
"templates": {
"cxx_client_opt": {
"baseTemplate": "default",
"clientImagePath": "/var/local/git/grpc/bins/opt/stress_test",
"metricsClientImagePath": "/var/local/git/grpc/bins/opt/metrics_client"
},
"cxx_client_tsan": {
"baseTemplate": "default",
"clientImagePath": "/var/local/git/grpc/bins/tsan/stress_test",
"metricsClientImagePath": "/var/local/git/grpc/bins/tsan/metrics_client"
},
"cxx_client_asan": {
"baseTemplate": "default",
"clientImagePath": "/var/local/git/grpc/bins/asan/stress_test",
"metricsClientImagePath": "/var/local/git/grpc/bins/asan/metrics_client"
}
}
},
"serverTemplates": {
"baseTemplates":{
"default": {
"wrapperScriptPath": "/var/local/git/grpc/tools/gcp/stress_test/run_server.py",
"serverPort": 8080,
"serverArgs": {
"port": 8080
}
}
},
"templates": {
"cxx_server_opt": {
"baseTemplate": "default",
"serverImagePath": "/var/local/git/grpc/bins/opt/interop_server"
},
"cxx_server_tsan": {
"baseTemplate": "default",
"serverImagePath": "/var/local/git/grpc/bins/tsan/interop_server"
},
"cxx_server_asan": {
"baseTemplate": "default",
"serverImagePath": "/var/local/git/grpc/bins/asan/interop_server"
}
}
},
"testMatrix": {
"serverPodSpecs": {
"stress-server-opt": {
"serverTemplate": "cxx_server_opt",
"dockerImage": "grpc_stress_cxx_opt",
"numInstances": 1
},
"stress-server-tsan": {
"serverTemplate": "cxx_server_tsan",
"dockerImage": "grpc_stress_cxx_tsan",
"numInstances": 1
},
"stress-server-asan": {
"serverTemplate": "cxx_server_asan",
"dockerImage": "grpc_stress_cxx_asan",
"numInstances": 1
}
},
"clientPodSpecs": {
"stress-client-opt": {
"clientTemplate": "cxx_client_opt",
"dockerImage": "grpc_stress_cxx_opt",
"numInstances": 3,
"serverPodSpec": "stress-server-opt"
},
"stress-client-tsan": {
"clientTemplate": "cxx_client_tsan",
"dockerImage": "grpc_stress_cxx_tsan",
"numInstances": 3,
"serverPodSpec": "stress-server-tsan"
},
"stress-client-asan": {
"clientTemplate": "cxx_client_asan",
"dockerImage": "grpc_stress_cxx_asan",
"numInstances": 3,
"serverPodSpec": "stress-server-asan"
}
}
},
"globalSettings": {
"buildDockerImages": true,
"pollIntervalSecs": 60,
"testDurationSecs": 7200,
"kubernetesProxyPort": 8001,
"datasetIdNamePrefix": "stress_test_opt_tsan",
"summaryTableId": "summary",
"qpsTableId": "qps",
"podWarmupSecs": 60
}
}
{
"dockerImages": {
"grpc_stress_cxx_opt" : {
"buildScript": "tools/jenkins/build_interop_stress_image.sh",
"dockerFileDir": "grpc_interop_stress_cxx",
"buildType": "opt"
}
},
"clientTemplates": {
"baseTemplates": {
"default": {
"wrapperScriptPath": "/var/local/git/grpc/tools/gcp/stress_test/run_client.py",
"pollIntervalSecs": 60,
"clientArgs": {
"num_channels_per_server":5,
"num_stubs_per_channel":10,
"test_cases": "empty_unary:1,large_unary:1,client_streaming:1,server_streaming:1,empty_stream:1",
"metrics_port": 8081,
"metrics_collection_interval_secs":60
},
"metricsPort": 8081,
"metricsArgs": {
"metrics_server_address": "localhost:8081",
"total_only": "true"
}
}
},
"templates": {
"cxx_client_opt": {
"baseTemplate": "default",
"clientImagePath": "/var/local/git/grpc/bins/opt/stress_test",
"metricsClientImagePath": "/var/local/git/grpc/bins/opt/metrics_client"
}
}
},
"serverTemplates": {
"baseTemplates":{
"default": {
"wrapperScriptPath": "/var/local/git/grpc/tools/gcp/stress_test/run_server.py",
"serverPort": 8080,
"serverArgs": {
"port": 8080
}
}
},
"templates": {
"cxx_server_opt": {
"baseTemplate": "default",
"serverImagePath": "/var/local/git/grpc/bins/opt/interop_server"
}
}
},
"testMatrix": {
"serverPodSpecs": {
"stress-server-opt": {
"serverTemplate": "cxx_server_opt",
"dockerImage": "grpc_stress_cxx_opt",
"numInstances": 1
}
},
"clientPodSpecs": {
"stress-client-opt": {
"clientTemplate": "cxx_client_opt",
"dockerImage": "grpc_stress_cxx_opt",
"numInstances": 10,
"serverPodSpec": "stress-server-opt"
}
}
},
"globalSettings": {
"buildDockerImages": true,
"pollIntervalSecs": 10,
"testDurationSecs": 120,
"kubernetesProxyPort": 8001,
"datasetIdNamePrefix": "stress_test_opt",
"summaryTableId": "summary",
"qpsTableId": "qps",
"podWarmupSecs": 60
}
}
This diff is collapsed.
This diff is collapsed.
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment