ElasticSearch系列整體欄目
內(nèi)容 | 鏈接地址 |
---|---|
【一】ElasticSearch下載和安裝 | https://zhenghuisheng.blog.csdn.net/article/details/129260827 |
【二】ElasticSearch概念和基本操作 | https://blog.csdn.net/zhenghuishengq/article/details/134121631 |
【三】ElasticSearch的高級(jí)查詢Query DSL | https://blog.csdn.net/zhenghuishengq/article/details/134159587 |
【四】ElasticSearch的聚合查詢操作 | https://blog.csdn.net/zhenghuishengq/article/details/134159587 |
【五】SpringBoot整合elasticSearch | https://blog.csdn.net/zhenghuishengq/article/details/134212200 |
一,SpringBoot整合ElasticSearch
前面幾篇講解了es的安裝,dsl語(yǔ)法,聚合查詢等,接下來(lái)這篇主要就是講解通過(guò)java的方式來(lái)操作es,這里選擇通過(guò)springboot的方式整合ElasticSearchSearch
在學(xué)習(xí)這個(gè)整合之前,可以查看對(duì)應(yīng)的官網(wǎng)資料:https://www.elastic.co/guide/en/elasticsearch/client/java-api-client/7.17/connecting.html
1,需要的依賴以及版本
首先創(chuàng)建springboot項(xiàng)目,然后需要的依賴如下,我前面用的是7.7.0的版本,因此這里繼續(xù)使用這個(gè)版本。其他的依賴根據(jù)個(gè)人需要選擇
<properties>
<java.version>8</java.version>
<elasticsearch.version>7.7.0</elasticsearch.version>
</properties>
<dependencies>
<dependency>
<groupId>org.elasticsearch.client</groupId>
<artifactId>elasticsearch-rest-high-level-client</artifactId>
<version>7.7.0</version>
</dependency>
</dependencies>
2,創(chuàng)建config配置類并測(cè)試連接
隨后創(chuàng)建一個(gè)config的配置類,用于連接上ElasticSearch,我這邊是單機(jī)版,并沒(méi)有集群
/**
* 連接es的工具類
*/
@Configuration
public class ElasticSearchConfig {
public static final RequestOptions COMMON_OPTIONS;
static {
RequestOptions.Builder builder = RequestOptions.DEFAULT.toBuilder();
COMMON_OPTIONS = builder.build();
}
@Bean
public RestHighLevelClient esRestClient(){
RestHighLevelClient client = new RestHighLevelClient(
RestClient.builder(new HttpHost("xx.xx.xx.xx", 9200, "http")));
return client;
}
}
在創(chuàng)建好了之后,可以直接在test類中進(jìn)行測(cè)試,看能否連接成功
@RunWith(SpringRunner.class)
@SpringBootTest
public class StudyApplicationTests {
@Resource
private RestHighLevelClient client;
@Test
public void contextLoads() {
System.out.println(restHighLevelClient);
}
}
在運(yùn)行之后,如果打印出了以下這句話,表示整合成功
org.elasticsearch.client.RestHighLevelClient@7d151a
3,增刪改查測(cè)試
3.1,索引插入數(shù)據(jù)
首先先創(chuàng)建一個(gè)users的索引,并向里面插入一條數(shù)據(jù)。插入和更新都可以用這個(gè)方法
//創(chuàng)建一個(gè)user索引,并且插入一條數(shù)據(jù)
@Test
public void addData() throws IOException {
//創(chuàng)建一個(gè)索引
IndexRequest userIndex = new IndexRequest("users");
User user = new User();
user.setId(1);
user.setUsername("Tom");
user.setPassword("123456");
user.setAge(18);
user.setSex("女");
//添加數(shù)據(jù)
userIndex.source(JSON.toJSONString(user), XContentType.JSON);
IndexResponse response = client.index(userIndex, ElasticSearchConfig.COMMON_OPTIONS);
//響應(yīng)數(shù)據(jù)
System.out.println(response);
}
隨后再在kibana中查詢這個(gè)索引,可以看到這條數(shù)據(jù)是已經(jīng)插入成功的,并且索引頁(yè)創(chuàng)建成功
3.2,根據(jù)id查詢數(shù)據(jù)
查詢id為1的數(shù)據(jù),需要通過(guò)QueryBuild構(gòu)造器查詢
@Test
public void getById() throws IOException {
SearchRequest request = new SearchRequest("users");
SearchSourceBuilder builder = new SearchSourceBuilder();
builder.query(QueryBuilders.matchQuery("id", "1"));
request.source(builder);
SearchResponse response = client.search(request, RequestOptions.DEFAULT);
System.out.println(response);
}
3.3,刪除一條數(shù)據(jù)
刪除剛剛創(chuàng)建的這條數(shù)據(jù),這里直接設(shè)置id為1即可
@Test
public void deleteById() throws Exception{
DeleteRequest request = new DeleteRequest("users");
request.id("1");
DeleteResponse delete = client.delete(request, ElasticSearchConfig.COMMON_OPTIONS);
System.out.println(delete);
}
4,普通查詢
這里主要是結(jié)合本人寫(xiě)的第三篇Query DSL的語(yǔ)法,通過(guò)java的方式寫(xiě)出依舊是先創(chuàng)建一個(gè)員工的信息索引,并且設(shè)置字段得我屬性
PUT /employees
{
"mappings": {
"properties": {
"name":{
"type": "keyword"
},
"job":{
"type": "keyword"
},
"salary":{
"type": "integer"
}
}
}
}
隨后批量的插入10條數(shù)據(jù)
PUT /employees/_bulk
{ "index" : { "_id" : "1" } }
{ "name" : "huisheng1","job":"python","salary":35000 }
{ "index" : { "_id" : "2" } }
{ "name" : "huisheng2","job":"java","salary": 50000}
{ "index" : { "_id" : "3" } }
{ "name" : "huisheng3","job":"python","salary":18000 }
{ "index" : { "_id" : "4" } }
{ "name" : "huisheng4","job":"java","salary": 22000}
{ "index" : { "_id" : "5" } }
{ "name" : "huisheng5","job":"javascript","salary":18000 }
{ "index" : { "_id" : "6" } }
{ "name" : "huisheng6","job":"javascript","salary": 25000}
{ "index" : { "_id" : "7" } }
{ "name" : "huisheng7","job":"c++","salary":20000 }
{ "index" : { "_id" : "8" } }
{ "name" : "huisheng8","job":"c++","salary": 20000}
{ "index" : { "_id" : "9" } }
{ "name" : "huisheng9","job":"java","salary":22000 }
{ "index" : { "_id" : "10" } }
{ "name" : "huisheng10","job":"java","salary": 9000}
4.1,match條件查詢
首先是分頁(yè)查詢,分頁(yè)查詢的queryDSL的語(yǔ)法如下
GET /employees/_search
{
"query": {
"match": {
"job": "java"
}
}
}
java的語(yǔ)法如下
SearchRequest request = new SearchRequest("employees");
SearchSourceBuilder builder = new SearchSourceBuilder();
builder.query(QueryBuilders.matchQuery("job", "java"));
request.source(builder);
SearchResponse response = client.search(request, RequestOptions.DEFAULT);
System.out.println(response);
短語(yǔ)匹配的語(yǔ)法如下
builder.query(QueryBuilders.matchPhraseQuery("job","java"));
多字段查詢的語(yǔ)法如下
String fields[] = {"job","name"};
builder.query(QueryBuilders.multiMatchQuery("java",fields));
queryString的語(yǔ)法如下
builder.query(QueryBuilders.queryStringQuery("java"));
4.2,term精確匹配
GET /employees/_search
{
"query": {
"term": {
"job": "java"
}
}
}
精確匹配通過(guò)java的方式如下
builder.query(QueryBuilders.termQuery("job","java"));
4.3,prefix前綴查詢
PUT /employees/_search
{
"query":{
"prefix":{
"name":{
"value":"huisheng1"
}
}
}
}
前綴查詢的java方式如下
builder.query(QueryBuilders.prefixQuery("name","huisheng1"));
4.4,通配符查詢wildcard
GET /employees/_search
{
"query": {
"wildcard": {
"job": {
"value": "*py*"
}
}
}
}
通配符查詢的java方式如下
builder.query(QueryBuilders.wildcardQuery("job","py"));
4.5,范圍查詢
POST /employees/_search
{
"query": {
"range": {
"salary": {
"gte": 25000
}
}
}
}
范圍查詢的java方式如下
builder.query(QueryBuilders.rangeQuery("salary").gte(25000));
4.6,fuzzy模糊查詢
GET /employees/_search
{
"query": {
"fuzzy": {
"job": {
"value": "javb",
"fuzziness": 1 //表示允許錯(cuò)一個(gè)字
}
}
}
}
模糊查詢的java方式如下
builder.query(QueryBuilders.fuzzyQuery("job","javb").fuzziness(Fuzziness.ONE));
4.7,highlight高亮查詢
GET /employees/_search
{
"query": {
"term": {
"job": {
"value": "java"
}
}
},
"highlight": {
"fields": {
"*":{}
}
}
}
高亮查詢的java方式如下
builder.query(QueryBuilders.termQuery("job","java"));
HighlightBuilder highlightBuilder = new HighlightBuilder();
highlightBuilder.field("job");
builder.highlighter(highlightBuilder);
5,聚合查詢
5.1,aggs聚合查詢
先通過(guò)job進(jìn)行分組查詢,再拿到結(jié)果后再進(jìn)行stats查詢,求最大值,最小值,平均值等
POST /employees/_search
{
"size": 0,
"aggs": {
"name": {
"terms": {
"field": "job"
},
"aggs": {
"stats_salary": {
"stats": {
"field": "salary"
}
}
}
}
}
}
其java代碼如下,需要注意的點(diǎn)就是,如果存在二級(jí)聚合,那么需要調(diào)用這個(gè) subAggregation 方法,如果只需要聚合的結(jié)果而不需要查詢的結(jié)果,可以直接在SearchSourceBuilder的實(shí)例設(shè)置為0即可。
@Test
public void toAgg() throws Exception{
//創(chuàng)建檢索請(qǐng)求
SearchRequest searchRequest = new SearchRequest();
//指定索引
searchRequest.indices("employees");
//構(gòu)建檢索條件
SearchSourceBuilder builder = new SearchSourceBuilder();
//構(gòu)建聚合條件
TermsAggregationBuilder aggregationBuilder = AggregationBuilders.terms("jobData").field("job");
aggregationBuilder.subAggregation(AggregationBuilders.stats("salaryData").field("salary"));
//將聚合條件加入到檢索條件中
builder.aggregation(aggregationBuilder);
//只要聚合的結(jié)果,不需要查詢的結(jié)果
builder.size(0);
searchRequest.source(builder);
//執(zhí)行檢索
SearchResponse searchResponse = client.search(searchRequest, RequestOptions.DEFAULT);
System.out.println("檢索結(jié)果:" + searchResponse);
}
打印的結(jié)果如下,和預(yù)期要打印的結(jié)果是一致的
{"took":4,"timed_out":false,"_shards":{"total":1,"successful":1,"skipped":0,"failed":0},"hits":{"total":{"value":10,"relation":"eq"},"max_score":null,"hits":[]},"aggregations":{"sterms#jobData":{"doc_count_error_upper_bound":0,"sum_other_doc_count":0,"buckets":[{"key":"java","doc_count":4,"stats#salaryData":{"count":4,"min":9000.0,"max":50000.0,"avg":25750.0,"sum":103000.0}},{"key":"c++","doc_count":2,"stats#salaryData":{"count":2,"min":20000.0,"max":20000.0,"avg":20000.0,"sum":40000.0}},{"key":"javascript","doc_count":2,"stats#salaryData":{"count":2,"min":18000.0,"max":25000.0,"avg":21500.0,"sum":43000.0}},{"key":"python","doc_count":2,"stats#salaryData":{"count":2,"min":18000.0,"max":35000.0,"avg":26500.0,"sum":53000.0}}]}}}
除了上面的state求全部的最大值,最小值等,還可以分別的求最大值,最小值,平均值,個(gè)數(shù)等,求平均值的的示例如下,需要使用到這個(gè) AvgAggregationBuilder 構(gòu)造器
AvgAggregationBuilder avgAggregationBuilder = AggregationBuilders.avg("salaryData").field("salary");
//將聚合條件加入到檢索條件中
builder.aggregation(avgAggregationBuilder);
求最大值的示例如下,需要使用到這個(gè) MaxAggregationBuilder 構(gòu)造器
MaxAggregationBuilder maxAggregationBuilder = AggregationBuilders.max("maxData").field("salary");
//將聚合條件加入到檢索條件中
builder.aggregation(maxAggregationBuilder);
求最小值的示例如下,需要使用到這個(gè) MinAggregationBuilder 構(gòu)造器
MinAggregationBuilder minAggregationBuilder = AggregationBuilders.min("minData").field("salary");
//將聚合條件加入到檢索條件中
builder.aggregation(minAggregationBuilder);
求總個(gè)數(shù)的示例如下,需要使用到這個(gè) ValueCountAggregationBuilder 構(gòu)造器
ValueCountAggregationBuilder countBuilder = AggregationBuilders.count("countData").field("salary");
//將聚合條件加入到檢索條件中
builder.aggregation(countBuilder);
5.2,獲取最終結(jié)果
上面在查詢之后,會(huì)獲取 SearchResponse 的對(duì)象,這里面就值執(zhí)行查詢后返回的結(jié)果
SearchResponse searchResponse
隨后可以直接過(guò)濾結(jié)果,通過(guò)for循環(huán)去遍歷這個(gè) getHits文章來(lái)源:http://www.zghlxwxcb.cn/news/detail-742377.html
SearchHits hits = searchResponse.getHits();
SearchHit[] searchHits = hits.getHits();
for (SearchHit searchHit : searchHits) {
String sourceAsString = searchHit.getSourceAsString();
Employees employees = JSON.parseObject(sourceAsString, Employees.class);
System.out.println(employees);
}
或者直接獲取聚合操作結(jié)果的值文章來(lái)源地址http://www.zghlxwxcb.cn/news/detail-742377.html
//獲取jobData聚合。還有Avg、Max、Min等
Terms maxData = aggregations.get("jobData");
for (Terms.Bucket bucket : maxData.getBuckets()) {
String keyAsString = bucket.getKeyAsString();
System.out.println("job職業(yè):" + keyAsString + " 數(shù)量==> " + bucket.getDocCount());
}
到了這里,關(guān)于【ElasticSearch系列-05】SpringBoot整合elasticSearch的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!