2016-11-18 11 views
3
sickern

ich Indizierung meiner Anfrage wie folgt:NEST Mit

client.Index(new PercolatedQuery 
{ 
    Id = "std_query", 
    Query = new QueryContainer(new MatchQuery 
    { 
     Field = Infer.Field<LogEntryModel>(entry => entry.Message), 
     Query = "just a text" 
    }) 
}, d => d.Index(EsIndex)); 

client.Refresh(EsIndex); 

Nun, wie verwende ich die percolator Fähigkeiten von ES mit dieser Abfrage ein eingehendes Dokument übereinstimmen? Zu sagen, dass die NEST-Dokumentation in diesem Bereich fehlt, wäre eine große Untertreibung. Ich habe versucht, client.Percolate Anruf mit, aber es ist jetzt veraltet und sie beraten die Suche api zu verwenden, aber nicht sagen, wie es zu benutzen mit Percolator ...

Ich verwende ES v5 und die gleiche Version von NEST lib.

Antwort

7

Es gibt Pläne, improve the documentation für 5.x, sobald die GA-Ausgabe aus ist; Ich verstehe, dass die Dokumentation an vielen Stellen klarer sein könnte und jede Hilfe in diesem Bereich am meisten geschätzt würde.

The documentation for the Percolate query wird von the integration test for it generiert. Ziehen Sie alle Stücke für ein Beispiel hier heraus, using details from you other question. Zuerst definieren wir die POCO-Modelle

public class LogEntryModel 
{ 
    public string Message { get; set; } 

    public DateTimeOffset Timestamp { get; set; } 
} 

public class PercolatedQuery 
{ 
    public string Id { get; set; } 

    public QueryContainer Query { get; set; } 
} 

Wir werden alle Eigenschaften fließend zuordnen, anstatt Mapping-Attribute zu verwenden. Die fließenden Mappings sind die mächtigsten und können alle in Elasticsearch abbildenden Wege ausdrücken.

Erstellen Sie jetzt die Verbindungseinstellungen und den Client, um mit Elasticsearch zu arbeiten.

var pool = new SingleNodeConnectionPool(new Uri($"http://localhost:9200")); 
var logIndex = "log_entries"; 
var connectionSettings = new ConnectionSettings(pool) 
    // infer mapping for logs 
    .InferMappingFor<LogEntryModel>(m => m 
     .IndexName(logIndex) 
     .TypeName("log_entry") 
    ) 
    // infer mapping for percolated queries 
    .InferMappingFor<PercolatedQuery>(m => m 
     .IndexName(logIndex) 
     .TypeName("percolated_query") 
    ); 

var client = new ElasticClient(connectionSettings); 

Wir können den Indexnamen und den Typnamen angeben, um auf unsere POCOs zu schließen; Das heißt, wenn NEST eine Anfrage unter Verwendung von LogEntryModel oder PercolatedQuery als den generischen Typparameter in einer Anfrage stellt (z. B. T in .Search<T>()), wird der abgeleitete Indexname und Typenname verwendet, wenn sie in der Anfrage nicht spezifiziert sind. Jetzt

, löschen Sie den Index, so dass wir von Grund auf neu

// delete the index if it already exists 
if (client.IndexExists(logIndex).Exists) 
    client.DeleteIndex(logIndex); 

und erstellen Sie den Index

client.CreateIndex(logIndex, c => c 
    .Settings(s => s 
     .NumberOfShards(1) 
     .NumberOfReplicas(0) 
    ) 
    .Mappings(m => m 
     .Map<LogEntryModel>(mm => mm 
      .AutoMap() 
     ) 
     .Map<PercolatedQuery>(mm => mm 
      .AutoMap() 
      .Properties(p => p 
       // map the query field as a percolator type 
       .Percolator(pp => pp 
        .Name(n => n.Query) 
       ) 
      ) 
     ) 
    ) 
); 

Die Query Eigenschaft auf dem PercolatedQuery abgebildet als percolator Typ beginnen. Dies ist neu in Elasticsearch 5.0. Die Mapping-Anfrage sieht aus wie

{ 
    "settings": { 
    "index.number_of_replicas": 0, 
    "index.number_of_shards": 1 
    }, 
    "mappings": { 
    "log_entry": { 
     "properties": { 
     "message": { 
      "fields": { 
      "keyword": { 
       "type": "keyword" 
      } 
      }, 
      "type": "text" 
     }, 
     "timestamp": { 
      "type": "date" 
     } 
     } 
    }, 
    "percolated_query": { 
     "properties": { 
     "id": { 
      "fields": { 
      "keyword": { 
       "type": "keyword" 
      } 
      }, 
      "type": "text" 
     }, 
     "query": { 
      "type": "percolator" 
     } 
     } 
    } 
    } 
} 

Jetzt können wir die Abfrage

client.Index(new PercolatedQuery 
{ 
    Id = "std_query", 
    Query = new MatchQuery 
    { 
     Field = Infer.Field<LogEntryModel>(entry => entry.Message), 
     Query = "just a text" 
    } 
}, d => d.Index(logIndex).Refresh(Refresh.WaitFor)); 

Mit der Abfrage indiziert Index bereit, lassen Sie uns ein Dokument versickern

var logEntry = new LogEntryModel 
{ 
    Timestamp = DateTimeOffset.UtcNow, 
    Message = "some log message text" 
}; 

// run percolator on the logEntry instance 
var searchResponse = client.Search<PercolatedQuery>(s => s 
    .Query(q => q 
     .Percolate(p => p 
      // field that contains the query 
      .Field(f => f.Query) 
      // details about the document to run the stored query against. 
      // NOTE: This does not index the document, only runs percolation 
      .DocumentType<LogEntryModel>() 
      .Document(logEntry) 
     ) 
    ) 
); 

// outputs 1 
Console.WriteLine(searchResponse.Documents.Count()); 

Die gelaufenen Abfrage mit id "std_query" kommt zurück in searchResponse.Documents

{ 
    "took" : 117, 
    "timed_out" : false, 
    "_shards" : { 
    "total" : 1, 
    "successful" : 1, 
    "failed" : 0 
    }, 
    "hits" : { 
    "total" : 1, 
    "max_score" : 0.2876821, 
    "hits" : [ 
     { 
     "_index" : "log_entries", 
     "_type" : "percolated_query", 
     "_id" : "std_query", 
     "_score" : 0.2876821, 
     "_source" : { 
      "id" : "std_query", 
      "query" : { 
      "match" : { 
       "message" : { 
       "query" : "just a text" 
       } 
      } 
      } 
     } 
     } 
    ] 
    } 
} 

Dies ist ein Beispiel für das Durchsuchen einer Dokumenteninstanz. Perkolation kann auch gegen bereits indizierte Dokumente ausgeführt werden

var searchResponse = client.Search<PercolatedQuery>(s => s 
    .Query(q => q 
     .Percolate(p => p 
      // field that contains the query 
      .Field(f => f.Query) 
      // percolate an already indexed log entry 
      .DocumentType<LogEntryModel>() 
      .Id("log entry id") 
      .Index<LogEntryModel>() 
      .Type<LogEntryModel>() 
     ) 
    ) 
); 
+2

Nicht jeder Held trägt Umhang.Mein Chef würde mir den Kopf abreißen, wenn ich bis Montag keine funktionierende Lösung hätte. Du hast buchstäblich mein Leben gerettet, also danke :). –

+0

Keine Sorge, ich bin froh, dass es geholfen hat :) –

+0

Vielen Dank für dieses nette Codeprobe des Percolators. –