public async Task ShouldNotThrowIfNotCanceled(
                RequestMessage request,
                [Target] DefaultRequestInvoker invoker,
                CancellationToken cancellationToken
                )
            {
                Func <Task> func = () => invoker.Invoke(request, cancellationToken);

                await func.Should().NotThrowAsync <OperationCanceledException>();
            }
            public async Task ShouldThrowIfCanceled(
                RequestMessage request,
                [Target] DefaultRequestInvoker invoker
                )
            {
                var         cancellationToken = new CancellationToken(true);
                Func <Task> func = () => invoker.Invoke(request, cancellationToken);

                await func.Should().ThrowAsync <OperationCanceledException>();
            }
            public async Task ShouldGetBucketAndWaitForAvailability(
                RequestMessage request,
                [Frozen] IBucketService service,
                [Target] DefaultRequestInvoker invoker,
                CancellationToken cancellationToken
                )
            {
                await invoker.Invoke(request, cancellationToken);

                await service.Received().GetBucketAndWaitForAvailability(Is(request.RequestDetails), Is(cancellationToken));
            }
            public async Task ShouldSendRequestWithCorrectMethod(
                RequestMessage request,
                [Frozen, Substitute] HttpMessageInvoker client,
                [Target] DefaultRequestInvoker invoker,
                CancellationToken cancellationToken
                )
            {
                await invoker.Invoke(request, cancellationToken);

                await client.Received().SendAsync(Any <HttpRequestMessage>(), Is(cancellationToken));

                var httpRequest = TestUtils.GetArg <HttpRequestMessage>(client, nameof(HttpMessageInvoker.SendAsync), 0);

                httpRequest.Method.Should().Be(request.RequestDetails.Endpoint.GetMethod());
            }
            public async Task ShouldUpdateBucketResetAfter(
                RequestMessage request,
                [Frozen] Bucket bucket,
                [Frozen] HttpResponseMessage responseMessage,
                [Frozen, Substitute] IBucketService bucketService,
                [Frozen, Substitute] HttpMessageInvoker client,
                [Frozen, Substitute] IUrlBuilder urlBuilder,
                [Target] DefaultRequestInvoker invoker,
                CancellationToken cancellationToken
                )
            {
                await invoker.Invoke(request, cancellationToken);

                bucketService.Received().UpdateBucketResetAfter(Is(bucket), Is(responseMessage));
            }
            public async Task ShouldSendRequestWithBuiltUrl(
                Uri url,
                RequestMessage request,
                [Frozen, Substitute] HttpMessageInvoker client,
                [Frozen, Substitute] IUrlBuilder urlBuilder,
                [Target] DefaultRequestInvoker invoker,
                CancellationToken cancellationToken
                )
            {
                urlBuilder.BuildFromRequest(Any <Request>()).Returns(url);
                await invoker.Invoke(request, cancellationToken);

                urlBuilder.Received().BuildFromRequest(Is(request.RequestDetails));
                await client.Received().SendAsync(Any <HttpRequestMessage>(), Is(cancellationToken));

                var httpRequest = TestUtils.GetArg <HttpRequestMessage>(client, nameof(HttpMessageInvoker.SendAsync), 0);

                httpRequest.RequestUri.Should().Be(url);
            }
            public async Task ShouldSendRequestWithNoBody(
                RequestMessage request,
                [Frozen, Substitute] HttpMessageInvoker client,
                [Frozen, Substitute] IUrlBuilder urlBuilder,
                [Target] DefaultRequestInvoker invoker,
                CancellationToken cancellationToken
                )
            {
                request.RequestDetails = new Request(ChannelEndpoint.CreateMessage)
                {
                    RequestBody = null
                };
                await invoker.Invoke(request, cancellationToken);

                await client.Received().SendAsync(Any <HttpRequestMessage>(), Is(cancellationToken));

                var httpRequest = TestUtils.GetArg <HttpRequestMessage>(client, nameof(HttpMessageInvoker.SendAsync), 0);

                httpRequest.Content.Should().BeNull();
            }
            public async Task ShouldSendRequestWithGivenBody(
                RequestMessage request,
                [Frozen, Substitute] HttpMessageInvoker client,
                [Frozen, Substitute] IUrlBuilder urlBuilder,
                [Target] DefaultRequestInvoker invoker,
                CancellationToken cancellationToken
                )
            {
                await invoker.Invoke(request, cancellationToken);

                await client.Received().SendAsync(Any <HttpRequestMessage>(), Is(cancellationToken));

                var httpRequest = TestUtils.GetArg <HttpRequestMessage>(client, nameof(HttpMessageInvoker.SendAsync), 0);

                var content       = httpRequest.Content.Should().BeOfType <StringContent>().Which;
                var contentString = await content.ReadAsStringAsync(cancellationToken);

                contentString.Should().Be(request.RequestDetails.RequestBody);
                content.Headers.ContentType !.MediaType.Should().BeEquivalentTo("application/json");
            }
            public async Task ShouldSaveChangesToTheBucket(
                string response,
                RequestMessage request,
                [Frozen] HttpStatusCode statusCode,
                [Frozen] Bucket bucket,
                [Frozen] HttpResponseMessage httpResponse,
                [Frozen, Substitute] HttpMessageInvoker client,
                [Frozen, Substitute] IBucketRepository repository,
                [Target] DefaultRequestInvoker invoker,
                CancellationToken cancellationToken
                )
            {
                httpResponse.Content   = new StringContent(response);
                request.RequestDetails = new Request(ChannelEndpoint.CreateMessage)
                {
                    RequestBody = null
                };
                await invoker.Invoke(request, cancellationToken);

                await repository.Received().Save(Is(bucket), Is(cancellationToken));
            }
            public async Task ShouldRespondToTheRequest(
                string response,
                RequestMessage request,
                [Frozen] HttpStatusCode statusCode,
                [Frozen] HttpResponseMessage httpResponse,
                [Frozen, Substitute] HttpMessageInvoker client,
                [Frozen, Substitute] IRequestMessageRelay relay,
                [Target] DefaultRequestInvoker invoker,
                CancellationToken cancellationToken
                )
            {
                httpResponse.Content   = new StringContent(response);
                request.RequestDetails = new Request(ChannelEndpoint.CreateMessage)
                {
                    RequestBody = null
                };
                await invoker.Invoke(request, cancellationToken);

                await client.Received().SendAsync(Any <HttpRequestMessage>(), Is(cancellationToken));

                await relay.Received().Respond(Is(request), Is(statusCode), Is(response), Is(cancellationToken));
            }
            public async Task ShouldFailRequestIfExceptionWasThrown(
                string response,
                RequestMessage request,
                [Frozen] HttpStatusCode statusCode,
                [Frozen] HttpResponseMessage httpResponse,
                [Frozen, Substitute] HttpMessageInvoker client,
                [Frozen, Substitute] IRequestMessageRelay relay,
                [Target] DefaultRequestInvoker invoker,
                CancellationToken cancellationToken
                )
            {
                client.SendAsync(Any <HttpRequestMessage>(), Any <CancellationToken>()).Throws <Exception>();
                request.RequestDetails = new Request(ChannelEndpoint.CreateMessage)
                {
                    RequestBody = null
                };

                await invoker.Invoke(request, cancellationToken);

                await client.Received().SendAsync(Any <HttpRequestMessage>(), Is(cancellationToken));

                await relay.Received().Fail(Is(request), Is(0U), Is(cancellationToken));
            }