public async Task UnaryServerHandler_NoAuth_Test(string methodName)
        {
            var helper       = new MockServiceBuilder();
            var unaryHandler = new UnaryServerMethod <string, string>((request, context) => Task.FromResult("ok"));
            var method       = new Method <string, string>(
                MethodType.Unary,
                nameof(PeerService),
                methodName,
                Marshallers.StringMarshaller,
                Marshallers.StringMarshaller);
            var serverServiceDefinition = ServerServiceDefinition.CreateBuilder()
                                          .AddMethod(method, (request, context) => unaryHandler(request, context)).Build()
                                          .Intercept(_authInterceptor);

            helper.ServiceDefinition = serverServiceDefinition;
            _server = helper.GetServer();
            _server.Start();

            _channel = helper.GetChannel();

            var result = await Calls.AsyncUnaryCall(new CallInvocationDetails <string, string>(_channel, method, default),
                                                    "");

            result.ShouldBe("ok");
        }
        public async Task ClientStreamingServerHandler_Auth_Failed()
        {
            var helper = new MockServiceBuilder();

            helper.ClientStreamingHandler = new ClientStreamingServerMethod <string, string>((request, context) => Task.FromResult("ok"));

            helper.ServiceDefinition = helper.ServiceDefinition.Intercept(_authInterceptor);
            _server = helper.GetServer();
            _server.Start();
            _channel = helper.GetChannel();

            await ShouldBeCancelRpcExceptionAsync(async() =>
                                                  await Calls.AsyncClientStreamingCall(helper.CreateClientStreamingCall()).ResponseAsync);

            var method = new Method <string, string>(MethodType.ClientStreaming, MockServiceBuilder.ServiceName, "ClientStreaming",
                                                     Marshallers.StringMarshaller, Marshallers.StringMarshaller);

            var peer = _peerPool.GetPeersByHost("127.0.0.1").First();

            ((GrpcPeer)peer).InboundSessionId = new byte[] { 1, 2, 3 };
            var callInvoker = helper.GetChannel().Intercept(metadata =>
            {
                metadata = new Metadata
                {
                    { GrpcConstants.PubkeyMetadataKey, peer.Info.Pubkey },
                    { GrpcConstants.SessionIdMetadataKey, new byte[] { 4, 5, 6 } }
                };
                return(metadata);
            });

            await ShouldBeCancelRpcExceptionAsync(async() =>
                                                  await callInvoker.AsyncClientStreamingCall(method, "localhost", new CallOptions()).ResponseAsync);
        }
        public async Task RetryDoesNotExceedSuccess()
        {
            var helper    = new MockServiceBuilder("localhost");
            int callCount = 0;

            helper.UnaryHandler = new UnaryServerMethod <string, string>((request, context) =>
            {
                callCount++;

                if (callCount == 1)
                {
                    context.Status = new Status(StatusCode.Cancelled, "");
                }

                return(Task.FromResult("ok"));
            });

            _server = helper.GetServer();
            _server.Start();
            _channel = helper.GetChannel();

            var callInvoker = helper.GetChannel().Intercept(new RetryInterceptor());

            var metadata = new Metadata {
                { GrpcConstants.RetryCountMetadataKey, "5" }
            };

            await callInvoker.AsyncUnaryCall(new Method <string, string>(MethodType.Unary,
                                                                         MockServiceBuilder.ServiceName, "Unary", Marshallers.StringMarshaller, Marshallers.StringMarshaller),
                                             "localhost", new CallOptions().WithHeaders(metadata), "");

            Assert.Equal(2, callCount);
        }
        public async Task RetryHeaderDecidesRetryCount()
        {
            var helper    = new MockServiceBuilder("localhost");
            int callCount = 0;

            helper.UnaryHandler = new UnaryServerMethod <string, string>((request, context) =>
            {
                callCount++;
                context.Status = new Status(StatusCode.Cancelled, "");
                return(Task.FromResult("ok"));
            });

            _server = helper.GetServer();
            _server.Start();
            _channel = helper.GetChannel();

            var callInvoker = helper.GetChannel().Intercept(new RetryInterceptor());

            var metadata = new Metadata {
                { GrpcConstants.RetryCountMetadataKey, "0" }
            };

            await Assert.ThrowsAsync <AggregateException>(async() => await callInvoker.AsyncUnaryCall(new Method <string, string>(MethodType.Unary,
                                                                                                                                  MockServiceBuilder.ServiceName, "Unary", Marshallers.StringMarshaller, Marshallers.StringMarshaller),
                                                                                                      "localhost", new CallOptions().WithHeaders(metadata), ""));

            Assert.Equal(1, callCount);

            callCount = 0;
            var oneRetryMetadata = new Metadata {
                { GrpcConstants.RetryCountMetadataKey, "1" }
            };

            await Assert.ThrowsAsync <AggregateException>(async() => await callInvoker.AsyncUnaryCall(new Method <string, string>(MethodType.Unary,
                                                                                                                                  MockServiceBuilder.ServiceName, "Unary", Marshallers.StringMarshaller, Marshallers.StringMarshaller),
                                                                                                      "localhost", new CallOptions().WithHeaders(oneRetryMetadata), ""));

            Assert.Equal(2, callCount);

            callCount = 0;

            await Assert.ThrowsAsync <AggregateException>(async() => await callInvoker.AsyncUnaryCall(new Method <string, string>(MethodType.Unary,
                                                                                                                                  MockServiceBuilder.ServiceName, "Unary", Marshallers.StringMarshaller, Marshallers.StringMarshaller),
                                                                                                      "localhost", new CallOptions(), ""));

            Assert.Equal(2, callCount);
        }
        public async Task Retry_Timeout_Test()
        {
            var helper    = new MockServiceBuilder("localhost");
            int callCount = 0;

            helper.UnaryHandler = new UnaryServerMethod <string, string>((request, context) =>
            {
                callCount++;

                Task.Delay(1000).Wait();

                return(Task.FromResult("ok"));
            });

            _server = helper.GetServer();
            _server.Start();
            _channel = helper.GetChannel();

            var callInvoker = helper.GetChannel().Intercept(new RetryInterceptor());

            var metadata = new Metadata {
                { GrpcConstants.RetryCountMetadataKey, "1" }
            };

            var exception = await Assert.ThrowsAsync <AggregateException>(async() => await callInvoker.AsyncUnaryCall(
                                                                              new Method <string, string>(MethodType.Unary,
                                                                                                          MockServiceBuilder.ServiceName, "Unary", Marshallers.StringMarshaller,
                                                                                                          Marshallers.StringMarshaller),
                                                                              "localhost", new CallOptions().WithHeaders(metadata), ""));

            var rpcException = exception.InnerExceptions[0] as RpcException;

            rpcException.ShouldNotBeNull();
            rpcException.StatusCode.ShouldBe(StatusCode.DeadlineExceeded);

            Assert.Equal(2, callCount);
        }
        public async Task UnaryServerHandler_Auth_Success()
        {
            var peer = _peerPool.GetPeersByHost("127.0.0.1").First();

            ((GrpcPeer)peer).InboundSessionId = new byte[] { 1, 2, 3 };

            var helper = new MockServiceBuilder();

            helper.UnaryHandler = new UnaryServerMethod <string, string>((request, context) =>
            {
                context.GetPeerInfo().ShouldBe(peer.ToString());
                return(Task.FromResult("ok"));
            });

            helper.ServiceDefinition = helper.ServiceDefinition.Intercept(_authInterceptor);
            _server = helper.GetServer();
            _server.Start();
            _channel = helper.GetChannel();

            var method = new Method <string, string>(MethodType.Unary, MockServiceBuilder.ServiceName, "Unary",
                                                     Marshallers.StringMarshaller, Marshallers.StringMarshaller);

            var callInvoker = helper.GetChannel().Intercept(metadata =>
            {
                metadata = new Metadata
                {
                    { GrpcConstants.PubkeyMetadataKey, peer.Info.Pubkey },
                    { GrpcConstants.SessionIdMetadataKey, new byte[] { 1, 2, 3 } }
                };
                return(metadata);
            });

            var result = await callInvoker.AsyncUnaryCall(method, "localhost", new CallOptions(), "");

            result.ShouldBe("ok");
        }