public static void ParseResponseReturnsParsedResponseGivenValidStream() { const int took = 2; const int shards = 1; const int hits = 1; const double score = 0.3141; const string index = "testIndex"; const string type = "testType"; const string id = "testId"; var responseString = BuildResponseString(took, shards, hits, score, index, type, id); using (var stream = new MemoryStream(Encoding.UTF8.GetBytes(responseString))) { var response = ElasticRequestProcessor.ParseResponse(stream, log); Assert.NotNull(response); Assert.Equal(took, response.took); Assert.Equal(shards, response._shards.successful); Assert.Equal(shards, response._shards.total); Assert.Equal(shards, response._shards.successful); Assert.Equal(0, response._shards.failed); Assert.Equal(hits, response.hits.total); Assert.Equal(score, response.hits.max_score); Assert.NotEmpty(response.hits.hits); Assert.Equal(score, response.hits.hits[0]._score); Assert.Equal(index, response.hits.hits[0]._index); Assert.Equal(type, response.hits.hits[0]._type); Assert.Equal(id, response.hits.hits[0]._id); } }
public static async Task ShouldCallElasticSearchClient() { var spyLog = new SpyLog(); var mockConnection = Substitute.For <IElasticConnection>(); mockConnection.Index.Returns("SearchIndex"); mockConnection.Options.Returns(new ElasticConnectionOptions()); mockConnection.Timeout.Returns(TimeSpan.FromSeconds(10)); var request = new SearchRequest { IndexType = "abc123", Size = 2112 }; var token = new CancellationToken(); var processor = new ElasticRequestProcessor(mockConnection, mapping, spyLog, retryPolicy); await processor.SearchAsync(request, token); #pragma warning disable 4014 // Remove this and await the SearchAsync below once NSubstitute 1.8.3 available mockConnection.Received(1).SearchAsync( #pragma warning restore 4014 @"{""size"":2112,""timeout"":""10s""}", request, token, spyLog ); }
public static async void SearchAsyncThrowsTaskCancelledExceptionWithSubsequentlyCancelledCancellationToken() { var request = new SearchRequest { IndexType = "docType" }; var processor = new ElasticRequestProcessor(connection, mapping, log, retryPolicy); var ex = await Record.ExceptionAsync(() => processor.SearchAsync(request, new CancellationTokenSource(500).Token)); Assert.IsType <TaskCanceledException>(ex); }
public static async void SearchAsyncThrowsTaskCancelledExceptionWithAlreadyCancelledCancellationToken() { var request = new SearchRequest { DocumentType = "docType" }; var processor = new ElasticRequestProcessor(connection, mapping, log, retryPolicy); var ex = await Record.ExceptionAsync(() => processor.SearchAsync(request, new CancellationToken(true))); Assert.IsType <TaskCanceledException>(ex); }
public VeryElasticQueryProvider(IElasticConnection connection, IElasticMapping mapping, IRetryPolicy retryPolicy) { Argument.CheckNotNull("connection", connection); Argument.CheckNotNull("mapping", mapping); Argument.CheckNotNull("retryPolicy", retryPolicy); this.Connection = connection; this.Mapping = mapping; this.RetryPolicy = retryPolicy; this.requestProcessor = new ElasticRequestProcessor(connection, mapping, retryPolicy); }
public static async Task NoAuthorizationWithEmptyUserName() { var messageHandler = new SpyMessageHandler(); var localConnection = new ElasticConnection(messageHandler, new Uri("http://localhost")); var processor = new ElasticRequestProcessor(localConnection, mapping, log, retryPolicy); var request = new ElasticSearchRequest { Type = "docType" }; await processor.SearchAsync(request); Assert.Null(messageHandler.Request.Headers.Authorization); }
/// <summary> /// Create a new ElasticQueryProvider for a given connection, mapping, log, retry policy and field prefix. /// </summary> /// <param name="connection">Connection to use to connect to Elasticsearch.</param> /// <param name="mapping">A mapping to specify how queries and results are translated.</param> /// <param name="log">A log to receive any information or debugging messages.</param> /// <param name="retryPolicy">A policy to describe how to handle network issues.</param> public ElasticQueryProvider(IElasticConnection connection, IElasticMapping mapping, ILog log, IRetryPolicy retryPolicy) { Argument.EnsureNotNull("connection", connection); Argument.EnsureNotNull("mapping", mapping); Argument.EnsureNotNull("log", log); Argument.EnsureNotNull("retryPolicy", retryPolicy); Connection = connection; Mapping = mapping; Log = log; RetryPolicy = retryPolicy; requestProcessor = new ElasticRequestProcessor(connection, mapping, log, retryPolicy); }
public static void NonSuccessfulHttpRequestThrows() { var messageHandler = new SpyMessageHandler(); messageHandler.Response.StatusCode = HttpStatusCode.NotFound; var localConnection = new ElasticConnection(messageHandler, new Uri("http://localhost"), "myUser", "myPass"); var processor = new ElasticRequestProcessor(localConnection, mapping, log, retryPolicy); var request = new ElasticSearchRequest { Type = "docType" }; var ex = Record.Exception(() => processor.SearchAsync(request).GetAwaiter().GetResult()); Assert.IsType <HttpRequestException>(ex); Assert.Equal("Response status code does not indicate success: 404 (Not Found).", ex.Message); }
public static async void NonSuccessfulHttpRequestThrows() { var messageHandler = new SpyMessageHandler { Response = { StatusCode = HttpStatusCode.NotFound } }; var localConnection = new ElasticConnection(messageHandler, new Uri("http://localhost"), "myUser", "myPass"); var processor = new ElasticRequestProcessor(localConnection, mapping, log, retryPolicy); var request = new SearchRequest { DocumentType = "docType" }; var ex = await Record.ExceptionAsync(() => processor.SearchAsync(request, CancellationToken.None)); Assert.IsType <HttpRequestException>(ex); Assert.Equal("Response status code does not indicate success: 404 (Not Found).", ex.Message); }
public static async Task ForcesBasicAuthorizationWhenProvidedWithUsernameAndPassword() { var messageHandler = new SpyMessageHandler(); var localConnection = new ElasticConnection(messageHandler, new Uri("http://localhost"), "myUser", "myPass"); var processor = new ElasticRequestProcessor(localConnection, mapping, log, retryPolicy); var request = new ElasticSearchRequest { Type = "docType" }; await processor.SearchAsync(request); var auth = messageHandler.Request.Headers.Authorization; Assert.NotNull(auth); Assert.Equal("Basic", auth.Scheme); Assert.Equal("myUser:myPass", Encoding.ASCII.GetString(Convert.FromBase64String(auth.Parameter))); }
public static async void SearchAsyncCapturesRequestInfoOnFailure() { var spyLog = new SpyLog(); var brokenConnection = new ElasticConnection(new Uri("http://localhost:12"), index: "MyIndex"); var processor = new ElasticRequestProcessor(brokenConnection, mapping, spyLog, new RetryPolicy(spyLog, 100, 1)); var searchRequest = new SearchRequest { IndexType = "docType" }; var formatter = new SearchRequestFormatter(brokenConnection, mapping, searchRequest); var ex = await Record.ExceptionAsync(() => processor.SearchAsync(searchRequest, CancellationToken.None)); Assert.IsType <RetryFailedException>(ex); var retryLogEntry = Assert.Single(spyLog.Entries, s => s.AdditionalInfo.ContainsKey("category") && s.AdditionalInfo["category"].Equals("retry")); Assert.Equal("MyIndex", retryLogEntry.AdditionalInfo["index"]); Assert.Equal(brokenConnection.GetSearchUri(searchRequest), retryLogEntry.AdditionalInfo["uri"]); Assert.Equal(formatter.Body, retryLogEntry.AdditionalInfo["query"]); }
public static async Task LogsDebugMessagesDuringExecution() { var responseString = BuildResponseString(2, 1, 1, 0.3141, "testIndex", "testType", "testId"); var messageHandler = new SpyMessageHandler(); var log = new SpyLog(); messageHandler.Response.Content = new StringContent(responseString); var localConnection = new ElasticConnection(messageHandler, new Uri("http://localhost"), "myUser", "myPass", index: "SearchIndex"); var processor = new ElasticRequestProcessor(localConnection, mapping, log, retryPolicy); var request = new ElasticSearchRequest { Type = "abc123", Size = 2112 }; await processor.SearchAsync(request); Assert.Equal(4, log.Messages.Count); Assert.Equal(@"[VERBOSE] Request: POST http://localhost/SearchIndex/abc123/_search", log.Messages[0]); Assert.Equal(@"[VERBOSE] Body: {""size"":2112,""timeout"":""10s""}", log.Messages[1]); Assert.True(new Regex(@"\[VERBOSE\] Response: 200 OK \(in \d+ms\)").Match(log.Messages[2]).Success); Assert.True(new Regex(@"\[VERBOSE\] De-serialized \d+ bytes into 1 hits in \d+ms").Match(log.Messages[3]).Success); }
public static async Task LogsDebugMessagesDuringExecution() { var responseString = BuildResponseString(2, 1, 1, 0.3141, "testIndex", "testType", "testId"); var messageHandler = new SpyMessageHandler(); var spyLog = new SpyLog(); messageHandler.Response.Content = new StringContent(responseString); var localConnection = new ElasticConnection(messageHandler, new Uri("http://localhost"), "myUser", "myPass", "SearchIndex"); var processor = new ElasticRequestProcessor(localConnection, mapping, spyLog, retryPolicy); var request = new SearchRequest { DocumentType = "abc123", Size = 2112 }; await processor.SearchAsync(request, CancellationToken.None); Assert.Equal(4, spyLog.Entries.Count); Assert.Equal(@"Request: POST http://localhost/SearchIndex/abc123/_search", spyLog.Entries[0].Message); Assert.Equal(@"Body:" + '\n' + @"{""size"":2112,""timeout"":""10s""}", spyLog.Entries[1].Message); Assert.True(new Regex(@"Response: 200 OK \(in \d+ms\)").Match(spyLog.Entries[2].Message).Success); Assert.True(new Regex(@"Deserialized \d+ bytes into 1 hits in \d+ms").Match(spyLog.Entries[3].Message).Success); }