예제 #1
0
        public async Task SequentialCreatesOnlyUseOneChannel()
        {
            //SpannerClients if created sequentially should only use a single channel.
            //This is to faciliate good session pool hits (which is per channel).  If we always
            //round robin'd clients, then we would get hard cache misses until we populated all
            //of the caches per channel.
            //Since channels are lazily created, this also saves resources for scenarios like rich clients
            //that may only need a single session for multiple sequential workloads.
            //Our default setting for # channels = 4 needs to work well for all scenarios.
            var firstReturnedClient = new Mock <SpannerClient>();
            var mockClientFactory   = SetupMockClientFactory(firstReturnedClient);

            var testPool       = new ClientPool(mockClientFactory);
            var expectedClient = firstReturnedClient.Object;

            Assert.Same(expectedClient, await testPool.AcquireClientAsync(s_defaultConnectionStringBuilder));
            testPool.ReleaseClient(expectedClient, s_defaultConnectionStringBuilder);

            Assert.Same(expectedClient, await testPool.AcquireClientAsync(s_defaultConnectionStringBuilder));
            testPool.ReleaseClient(expectedClient, s_defaultConnectionStringBuilder);

            Assert.Same(expectedClient, await testPool.AcquireClientAsync(s_defaultConnectionStringBuilder));
            testPool.ReleaseClient(expectedClient, s_defaultConnectionStringBuilder);

            var s = new StringBuilder();

            Assert.Equal(0, testPool.GetPoolInfo(s));
            Logger.DefaultLogger.Info(() => s.ToString());
            Assert.Equal(1, mockClientFactory.Invocations);
        }
예제 #2
0
        private static async Task <SpannerClient> GetSpannerClientAsync(ClientPool pool)
        {
            //immediately yield to increase contention for stress testing.
            await Task.Yield();

            return(await pool.AcquireClientAsync(s_defaultConnectionStringBuilder));
        }
예제 #3
0
        public async Task RoundRobin()
        {
            var mockClientFactory = SetupMockClientFactory();

            var testPool = new ClientPool(mockClientFactory);

            var clientList = new List <SpannerClient>();

            for (var i = 0; i < SpannerOptions.Instance.MaximumGrpcChannels; i++)
            {
                var newClient = await testPool.AcquireClientAsync(s_defaultConnectionStringBuilder);

                Assert.DoesNotContain(newClient, clientList);
                clientList.Add(newClient);
            }

            //now we wrap around.
            var firstReusedClient = await testPool.AcquireClientAsync(s_defaultConnectionStringBuilder);

            Assert.Same(clientList[0], firstReusedClient);
            testPool.ReleaseClient(firstReusedClient, s_defaultConnectionStringBuilder);

            foreach (var client in clientList)
            {
                testPool.ReleaseClient(client, s_defaultConnectionStringBuilder);
            }
            var s = new StringBuilder();

            Assert.Equal(0, testPool.GetPoolInfo(s));
            Logger.DefaultLogger.Info(() => s.ToString());

            //now that everything got released, lets ensure the client order is preserved so
            //that we again get the first client.
            Assert.Same(firstReusedClient, await testPool.AcquireClientAsync(s_defaultConnectionStringBuilder));
            testPool.ReleaseClient(firstReusedClient, s_defaultConnectionStringBuilder);

            Assert.Equal(SpannerOptions.Instance.MaximumGrpcChannels, mockClientFactory.Invocations);
        }
예제 #4
0
        public async Task ClientsCreatedOnDemandAsync()
        {
            //SpannerClients should not be precreated, but be created lazily.
            var mockClientFactory = SetupMockClientFactory();

            var testPool       = new ClientPool(mockClientFactory);
            var clientAcquired = await testPool.AcquireClientAsync(s_defaultConnectionStringBuilder);

            testPool.ReleaseClient(clientAcquired, s_defaultConnectionStringBuilder);

            Assert.Equal(1, mockClientFactory.Invocations);
            var s = new StringBuilder();

            Assert.Equal(0, testPool.GetPoolInfo(s));
            Logger.DefaultLogger.Info(() => s.ToString());
        }