public GatewayAddressCache( Uri serviceEndpoint, Protocol protocol, IAuthorizationTokenProvider tokenProvider, IServiceConfigurationReader serviceConfigReader, CosmosHttpClient httpClient, long suboptimalPartitionForceRefreshIntervalInSeconds = 600, bool enableTcpConnectionEndpointRediscovery = false) { this.addressEndpoint = new Uri(serviceEndpoint + "/" + Paths.AddressPathSegment); this.protocol = protocol; this.tokenProvider = tokenProvider; this.serviceEndpoint = serviceEndpoint; this.serviceConfigReader = serviceConfigReader; this.serverPartitionAddressCache = new AsyncCache <PartitionKeyRangeIdentity, PartitionAddressInformation>(); this.suboptimalServerPartitionTimestamps = new ConcurrentDictionary <PartitionKeyRangeIdentity, DateTime>(); this.serverPartitionAddressToPkRangeIdMap = new ConcurrentDictionary <ServerKey, HashSet <PartitionKeyRangeIdentity> >(); this.suboptimalMasterPartitionTimestamp = DateTime.MaxValue; this.enableTcpConnectionEndpointRediscovery = enableTcpConnectionEndpointRediscovery; this.suboptimalPartitionForceRefreshIntervalInSeconds = suboptimalPartitionForceRefreshIntervalInSeconds; this.httpClient = httpClient; this.protocolFilter = string.Format(CultureInfo.InvariantCulture, GatewayAddressCache.protocolFilterFormat, Constants.Properties.Protocol, GatewayAddressCache.ProtocolString(this.protocol)); }
/// <summary> /// Task to collect virtual machine metadata information. using instance metedata service API. /// ref: https://docs.microsoft.com/en-us/azure/virtual-machines/windows/instance-metadata-service?tabs=windows /// Collects only application region and environment information /// </summary> /// <returns>Async Task</returns> internal static async Task <AzureVMMetadata> LoadAzureVmMetaDataAsync(CosmosHttpClient httpClient) { if (azMetadata == null) { DefaultTrace.TraceVerbose("Getting VM Metadata Information for Telemetry."); try {
public async Task GatewayStoreClientTimeout() { using (CosmosClient client = TestCommon.CreateCosmosClient(useGateway: true)) { // Creates the store clients in the document client await client.DocumentClient.EnsureValidClientAsync(); // Get the GatewayStoreModel GatewayStoreModel gatewayStore; using (DocumentServiceRequest serviceRequest = new DocumentServiceRequest( operationType: OperationType.Read, resourceIdOrFullName: null, resourceType: ResourceType.Database, body: null, headers: null, isNameBased: false, authorizationTokenType: AuthorizationTokenType.PrimaryMasterKey)) { serviceRequest.UseGatewayMode = true; gatewayStore = (GatewayStoreModel)client.DocumentClient.GetStoreProxy(serviceRequest); } DocumentClient documentClient = client.DocumentClient; FieldInfo cosmosHttpClientProperty = client.DocumentClient.GetType().GetField("httpClient", BindingFlags.NonPublic | BindingFlags.Instance); CosmosHttpClient cosmosHttpClient = (CosmosHttpClient)cosmosHttpClientProperty.GetValue(documentClient); // Set the http request timeout to 10 ms to cause a timeout exception HttpClient httpClient = new HttpClient(new TimeOutHttpClientHandler()); FieldInfo httpClientProperty = cosmosHttpClient.GetType().GetField("httpClient", BindingFlags.NonPublic | BindingFlags.Instance); httpClientProperty.SetValue(cosmosHttpClient, httpClient); FieldInfo gatewayRequestTimeoutProperty = cosmosHttpClient.GetType().GetField("GatewayRequestTimeout", BindingFlags.NonPublic | BindingFlags.Static); gatewayRequestTimeoutProperty.SetValue(cosmosHttpClient, TimeSpan.FromSeconds(1)); // Verify the failure has the required info try { await client.CreateDatabaseAsync("TestGatewayTimeoutDb" + Guid.NewGuid().ToString()); Assert.Fail("Operation should have timed out:"); } catch (CosmosException rte) { string message = rte.ToString(); Assert.IsTrue(message.Contains("Start Time"), "Start Time:" + message); Assert.IsTrue(message.Contains("Total Duration"), "Total Duration:" + message); Assert.IsTrue(message.Contains("Http Client Timeout"), "Http Client Timeout:" + message); Assert.IsTrue(message.Contains("Activity id"), "Activity id:" + message); } } }
public async Task HttpClientConnectionLimitTest() { int gatewayConnectionLimit = 1; IReadOnlyList <string> excludeConnections = GetActiveConnections(); CosmosClient cosmosClient = new CosmosClient( ConfigurationManager.AppSettings["GatewayEndpoint"], ConfigurationManager.AppSettings["MasterKey"], new CosmosClientOptions { ApplicationName = "test", GatewayModeMaxConnectionLimit = gatewayConnectionLimit, ConnectionMode = ConnectionMode.Gateway, ConnectionProtocol = Protocol.Https } ); FieldInfo httpClient = cosmosClient.DocumentClient.GetType().GetField("httpClient", BindingFlags.NonPublic | BindingFlags.Instance); CosmosHttpClient cosmosHttpClient = (CosmosHttpClient)httpClient.GetValue(cosmosClient.DocumentClient); HttpClientHandler httpClientHandler = (HttpClientHandler)cosmosHttpClient.HttpMessageHandler; Assert.AreEqual(gatewayConnectionLimit, httpClientHandler.MaxConnectionsPerServer); Cosmos.Database database = await cosmosClient.CreateDatabaseAsync(Guid.NewGuid().ToString()); Container container = await database.CreateContainerAsync( "TestConnections", "/pk", throughput : 20000); List <Task> creates = new List <Task>(); for (int i = 0; i < 100; i++) { creates.Add(container.CreateItemAsync <dynamic>(new { id = Guid.NewGuid().ToString(), pk = Guid.NewGuid().ToString() })); } await Task.WhenAll(creates); // Verify the handler still exists after client warm up //Assert.AreEqual(gatewayConnectionLimit, httpClientHandler.MaxConnectionsPerServer); IReadOnlyList <string> afterConnections = GetActiveConnections(); // Clean up the database and container await database.DeleteAsync(); int connectionDiff = afterConnections.Count - excludeConnections.Count; Assert.IsTrue(connectionDiff <= gatewayConnectionLimit, $"Connection before : {excludeConnections.Count}, after {afterConnections.Count}"); }
public async Task HttpClientConnectionLimitTest() { int gatewayConnectionLimit = 1; IReadOnlyList <string> excludeConnections = GetActiveConnections(); using (CosmosClient cosmosClient = new CosmosClient( ConfigurationManager.AppSettings["GatewayEndpoint"], ConfigurationManager.AppSettings["MasterKey"], new CosmosClientOptions { ApplicationName = "test", GatewayModeMaxConnectionLimit = gatewayConnectionLimit, ConnectionMode = ConnectionMode.Gateway, ConnectionProtocol = Protocol.Https } )) { CosmosHttpClient cosmosHttpClient = cosmosClient.DocumentClient.httpClient; HttpClientHandler httpClientHandler = (HttpClientHandler)cosmosHttpClient.HttpMessageHandler; Assert.AreEqual(gatewayConnectionLimit, httpClientHandler.MaxConnectionsPerServer); Cosmos.Database database = await cosmosClient.CreateDatabaseAsync(Guid.NewGuid().ToString()); Container container = await database.CreateContainerAsync( "TestConnections", "/pk", throughput : 20000); List <Task> creates = new List <Task>(); for (int i = 0; i < 100; i++) { creates.Add(container.CreateItemAsync <dynamic>(new { id = Guid.NewGuid().ToString(), pk = Guid.NewGuid().ToString() })); } await Task.WhenAll(creates); // Clean up the database and container await database.DeleteAsync(); } IReadOnlyList <string> afterConnections = GetActiveConnections(); int connectionDiff = afterConnections.Count - excludeConnections.Count; Assert.IsTrue(connectionDiff <= gatewayConnectionLimit, $"Connection before : {excludeConnections.Count}, after {afterConnections.Count};" + $"Before connections: {JsonConvert.SerializeObject(excludeConnections)}; After connections: {JsonConvert.SerializeObject(afterConnections)}"); }
public void VerifyHttpClientHandlerIsSet() { string endpoint = AccountEndpoint; string key = "425Mcv8CXQqzRNCgFNjIhT424GK99CKJvASowTnq15Vt8LeahXTcN5wt3342vQ=="; IWebProxy webProxy = new TestWebProxy(); CosmosClientBuilder cosmosClientBuilder = new CosmosClientBuilder( accountEndpoint: endpoint, authKeyOrResourceToken: key); cosmosClientBuilder.WithConnectionModeGateway( maxConnectionLimit: null, webProxy: webProxy); CosmosClient cosmosClient = cosmosClientBuilder.Build(); CosmosHttpClient cosmosHttpClient = cosmosClient.DocumentClient.httpClient; HttpClientHandler handler = (HttpClientHandler)cosmosHttpClient.HttpMessageHandler; Assert.IsTrue(object.ReferenceEquals(webProxy, handler.Proxy)); }
public GlobalAddressResolver( GlobalEndpointManager endpointManager, GlobalPartitionEndpointManager partitionKeyRangeLocationCache, Protocol protocol, ICosmosAuthorizationTokenProvider tokenProvider, CollectionCache collectionCache, PartitionKeyRangeCache routingMapProvider, IServiceConfigurationReader serviceConfigReader, ConnectionPolicy connectionPolicy, CosmosHttpClient httpClient) { this.endpointManager = endpointManager; this.partitionKeyRangeLocationCache = partitionKeyRangeLocationCache; this.protocol = protocol; this.tokenProvider = tokenProvider; this.collectionCache = collectionCache; this.routingMapProvider = routingMapProvider; this.serviceConfigReader = serviceConfigReader; this.httpClient = httpClient; int maxBackupReadEndpoints = !connectionPolicy.EnableReadRequestsFallback.HasValue || connectionPolicy.EnableReadRequestsFallback.Value ? GlobalAddressResolver.MaxBackupReadRegions : 0; this.enableTcpConnectionEndpointRediscovery = connectionPolicy.EnableTcpConnectionEndpointRediscovery; this.maxEndpoints = maxBackupReadEndpoints + 2; // for write and alternate write endpoint (during failover) this.addressCacheByEndpoint = new ConcurrentDictionary <Uri, EndpointCache>(); foreach (Uri endpoint in endpointManager.WriteEndpoints) { this.GetOrAddEndpoint(endpoint); } foreach (Uri endpoint in endpointManager.ReadEndpoints) { this.GetOrAddEndpoint(endpoint); } }
public async Task ResponseMessageHasRequestMessageAsync() { // We don't set the RequestMessage property on purpose on the Failed response // This will make it go through GatewayStoreClient.CreateDocumentClientExceptionAsync Func <HttpRequestMessage, Task <HttpResponseMessage> > sendFunc = request => { HttpResponseMessage response = new HttpResponseMessage(HttpStatusCode.NotFound) { Content = new StringContent("test") }; return(Task.FromResult(response)); }; DocumentClientEventSource eventSource = DocumentClientEventSource.Instance; HttpMessageHandler messageHandler = new MockMessageHandler(sendFunc); CosmosHttpClient cosmoshttpClient = MockCosmosUtil.CreateCosmosHttpClient(() => new HttpClient(messageHandler)); HttpRequestMessage httpRequestMessage = new HttpRequestMessage(HttpMethod.Post, new Uri("http://localhost")); HttpResponseMessage responseMessage = await cosmoshttpClient.SendHttpAsync(() => new ValueTask <HttpRequestMessage>(httpRequestMessage), ResourceType.Collection, null, default); Assert.AreEqual(httpRequestMessage, responseMessage.RequestMessage); }