Using the percolator, you can register queries against one or multiple indices and then you can send percolate requests with a document which return which registered queries it matched.
The percolator has been available in the product since the version 0.15, however starting from version 1.0 a fully distributed version of percolator will be available. The redesigned percolator will have a _percolator type mapping instead of a _percolator index, and the query and data will coexist with the same index. The redesigned percolator is also fixing the confusing part of the query registration API where the index name was represented as the type in the _percolator index. In the redesigned percolator this confusion is gone, because the _percolator became a type
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
curl -XPUT 'http://localhost:9200/households/_percolator/my_id' -d { | |
"query": { | |
... | |
} | |
} |
Let's consider the following model
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class Household { | |
private String id; | |
private String description; | |
private Double lat; | |
private Double lon; | |
private int price; | |
private Date postDate; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
private void addGeoTypeMapping() throws IOException { | |
XContentBuilder mapping = jsonBuilder() | |
.startObject() | |
.startObject("household") | |
.startObject("properties") | |
.startObject("location") | |
.field("type", "geo_point") | |
.endObject() | |
.endObject() | |
.endObject() | |
.endObject(); | |
client.admin().indices().prepareCreate("households") | |
.addMapping("household", mapping).execute().actionGet(); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
private FilterBuilder filterBuilder() { | |
return boolFilter() | |
.must(rangeFilter("price").from("250000").to("300000")) | |
.must(geoDistanceFilter("location") | |
.point(52.09, 5.11) | |
.distance(5, DistanceUnit.KILOMETERS) | |
); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
client.prepareIndex("households", "_percolator", "myQuery") | |
.setSource(jsonBuilder() | |
.startObject() | |
.field("query", constantScoreQuery(filterBuilder())) | |
.field("user_id", "123") | |
.endObject()) | |
.setRefresh(true) // Needed when the query shall be available immediately | |
.execute().actionGet(); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// create a source of the percolate request | |
XContentBuilder docBuilder = jsonBuilder() | |
.startObject() | |
.field("doc") | |
.startObject() | |
.startObject("location") | |
.field("lat", 52.10) | |
.field("lon", 5.12) | |
.endObject() | |
.field("price", 290000) | |
.endObject() | |
.endObject(); | |
// send the percolate request | |
PercolateResponse response = client.preparePercolate() | |
.setIndices("households") | |
.setDocumentType("household") | |
.setSource(docBuilder) | |
.execute().actionGet(); | |
assertThat(response.getCount(), is(1L)); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
GetResponse matchedQuery = client.prepareGet("households","_percolator", "myQuery") | |
.setFetchSource("user_id", "query") | |
.execute().actionGet(); | |
assertThat(((String) matchedQuery.getSource().get("user_id")), is("123")); | |
assertThat(matchedQuery.getSource().get("query"), is(nullValue())); |
2 comments:
Hi,
Great example, i'm still a bit confused with regards to what you have to build.
I thought that if you register a query and a new document is indexed, ES itself would percolate and send a message to a user (publish-subscribe)
What i read here is that you need to build a tool that continually does percolator requests (maybe as part of the tool that indexes new documents).
What am i missing?
Thanks,
Maarten
Maarten, that has changed since ElasticSearch 1.0 onwards.
See Luca Cavanna's comment just below the quersion
If you mean percolate while indexing, it's possible with 0.90 but removed with the new percolator in master (1.0). The reason for the removal is that it is the bigger piece that prevented the percolator from being distributed in 0.90, as you need both the queries and the documents in the same node in order for it to be performant. Makes sense?
Source - http://stackoverflow.com/questions/20960135/is-it-possible-to-get-back-a-response-from-the-percolator-when-inserting-a-docum
Post a Comment