02.ElasticSearch(SpringDataElasticSearch)
1. 概述
Spring Data Elasticsearch 对原生的 Elasticsearch 简化
特点:
- 基于Configuration配置,只要在yml文件中配置,项目就可以使用
- 工具类 ElasticsearchTemplate ES模板,类似女通用mapper,通过对象操作ES
- 提供持久层接口 Repository,无需编写基本操作代码(蕾西与mybatis,根据接口自动得到实现),也支持自定义查询
2. 环境搭建
步骤一: 修改pom.xml文件,导入坐标
步骤二: 修改yml文件,添加Elasticsearch配置信息
步骤三: 创建一个配置类,项目启动时时,设置一个参数,防止运行时异常
步骤四: 编写测试方法
步骤一: 修改pom.xml文件,导入坐标
<dependencies>
<!--redis-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
<groupId>redis.clients</groupId>
<artifactId>jedis</artifactId>
</dependency>
<!--测试-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
</dependency>
<dependency>
<groupId>com.czxy</groupId>
<artifactId>changgou_common</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
<!--es-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-elasticsearch</artifactId>
</dependency>
</dependencies>
步骤二: 修改yml文件,添加Elasticsearch配置信息
spring:
redis:
database: 1 #确定使用库
host: 127.0.0.1 #redis服务地址
port: 6379 #redis 端口号
data:
elasticsearch:
cluster-name: elasticsearch
cluster-nodes: 127.0.0.1:9300
步骤三: 创建一个配置类,项目启动时时,设置一个参数,防止运行时异常
package com.czxy.config;
import org.springframework.context.annotation.Configuration;
import javax.annotation.PostConstruct;
/**
* Created by Pole丶逐.
*/
@Configuration
public class ESConfig {
/**
* 项目启动时,设置一个参数
*/
@PostConstruct
public void init() {
System.setProperty("es.set.netty.runtime.available.processors", "false");
}
}
步骤四: 编写测试方法
package com.czxy.test;
import com.czxy.TestApplication;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;
/**
* [@Author](https://my.oschina.net/arthor) Pole丶逐
* [@Date](https://my.oschina.net/u/2504391) 2020/4/13 20:39
* [@E-mail](https://my.oschina.net/rosolio)
*/
@RunWith(SpringRunner.class)
@SpringBootTest(classes = TestApplication.class)
public class Demo01 {
@Test
public void test(){
System.out.println("AAA");
}
}
3. 索引操作
3.1 创建映射类
映射类: 用于表示java数据和Elasticsearch中数据对应关系.在Spring Data Elasticsearch使用注解完成
名称 修饰位置 参数 @Document
表示java数据和Elasticsearch中数据对应关系
indexName: 对应索引名称<br/>type: 对应索引库中的类型 <br/>shards: 分片数量 <br/>replicas: 副本数量
@Id
唯一标识
无
@Field
java属性和es字段的对应关系
type: 字段类型<br/>analyzer: 分词器名称<br/>index: 是否索引,默认为true<br/>store: 是否存储,默认为false
实现类:
package com.czxy.vo;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.data.annotation.Id;
import org.springframework.data.elasticsearch.annotations.Document;
import org.springframework.data.elasticsearch.annotations.Field;
import org.springframework.data.elasticsearch.annotations.FieldType;
/**
* @Author Pole丶逐
* @Date 2020/4/13 20:55
* @E-mail
*/
@NoArgsConstructor
@AllArgsConstructor
@Data
@Document(indexName = "czxy56",type = "book",shards = 4,replicas = 2)
public class ESBook {
@Id
private Long id;
@Field(type = FieldType.Text,analyzer = "ik_max_word")
private String title;
@Field(type = FieldType.Keyword)
private String images;
@Field(type = FieldType.Float)
private Double price;
}
3.2 创建索引,添加映射,删除索引
ElasticsearchTemplate工具类提供对应方法完成以下功能
步骤一: 直接注入ElasticsearchTemplate,spring容器中自动创建
步骤二: 调用对应API操作
package com.czxy.test;
import com.czxy.TestApplication;
import com.czxy.vo.ESBook;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.elasticsearch.core.ElasticsearchTemplate;
import org.springframework.test.context.junit4.SpringRunner;
import javax.annotation.Resource;
/**
* @Author Pole丶逐
* @Date 2020/4/13 21:00
* @E-mail
*/
@RunWith(SpringRunner.class)
@SpringBootTest(classes = TestApplication.class)
public class TestES {
@Resource
private ElasticsearchTemplate elasticsearchTemplate;
@Test
public void test1(){
// 创建索引
elasticsearchTemplate.createIndex(ESBook.class);
}
@Test
public void test2(){
//创建映射
elasticsearchTemplate.putMapping(ESBook.class);
}
@Test
public void test3(){
//删除索引
elasticsearchTemplate.deleteIndex(ESBook.class);
}
}
4. 文档操作(增删改)
实现接口: ElasticsearchRepository,实现了所有功能
只需要继承 **ElasticsearchRepository **接口即可,Spring Data 自动加载
参数类型: 泛型
第一个: 映射类(ESBook)
第二个: 映射类唯一标识的类型(Id)
package com.czxy.repository;
import com.czxy.vo.ESBook;
import org.springframework.data.elasticsearch.repository.ElasticsearchRepository;
import java.util.List;
/**
* @Author Pole丶逐
* @Date 2020/4/13 21:15
* @E-mail
*/
public interface ESBookRepository extends ElasticsearchRepository<ESBook,Long> {
}
4.1 添加数据
方法名 描述
save()
添加一个数据
saveAll()
添加一组数据
package com.czxy.test;import com.czxy.TestApplication;
import com.czxy.repository.ESBookRepository;
import com.czxy.vo.ESBook;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;
import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Optional;
/**
* @Author Pole丶逐
* @Date 2020/4/13 21:14
* @E-mail
*/
@RunWith(SpringRunner.class)
@SpringBootTest(classes = TestApplication.class)
public class TestESData {
@Resource
private ESBookRepository esBookRepository;
@Test
public void test1(){
//添加一个数据
esBookRepository.save(new ESBook(1L,"时间简史","01.jpg",35.0));
}
@Test
public void test2(){
ArrayList<ESBook> eslist = new ArrayList<>();
eslist.add(new ESBook(1L,"时间简史","01.jpg",35.0));
eslist.add(new ESBook(2L,"三体","02.jpg",40.0));
eslist.add(new ESBook(3L, "人类简史","03.jpg",35.5));
//添加一个集合
esBookRepository.saveAll(eslist);
}
}
4.2 修改数据
修改和添加使用的是一个方法
- 如果id存在则为修改
- 如果id不存在则为添加
@Test
public void test1(){
//修改数据,id必须存在,否则为添加
esBookRepository.save(new ESBook(1L,"空间简史","01.jpg",35.0));
}
4.2 删除数据
@Testpublic void test3(){
// 根据对象删除
//esBookRepository.delete();
// 根据id删除
//esBookRepository.deleteById(1L);
// 删除所有
//esBookRepository.deleteAll();
}
5. 查询
5.1 基本查询
方法 描述
findAll()
查询所有
findById()
根据id查询
@Testpublic void test4(){
//查询所有
Iterable<ESBook> iterable = esBookRepository.findAll();
Iterator<ESBook> iterator = iterable.iterator();
while (iterator.hasNext()){
ESBook esBook = iterator.next();
System.out.println(esBook);
}
}
@Test
public void test5(){
//根据id查询
Optional<ESBook> optional = esBookRepository.findById(1L);
ESBook esBook = optional.get();
System.out.println(esBook);
}
5.2 自定义方法
Spring Data 根据约定的方法名进行自动查询
- 要求: findBy字段 | 关键字
实例:
package com.czxy.repository;
import com.czxy.vo.ESBook;
import org.springframework.data.elasticsearch.repository.ElasticsearchRepository;
import java.util.List;
/**
* @Author Pole丶逐
* @Date 2020/4/13 21:15
* @E-mail
*/
public interface ESBookRepository extends ElasticsearchRepository<ESBook,Long> {
//根据title查询
List<ESBook> findByTitle(String title);
//根据price查询区间
List<ESBook> findByPriceBetween(Double start, Double end);
//查询大于等于price
List<ESBook> findByPriceGreaterThanEqual(Double price);
}
5.3 自定义查询
5.3.1 关键字查询: match
查询条件构造器: NativeSearchQueryBuilder
查询: queryBuilder.withQuery( ... )
match条件: QueryBuilders.matchQuery("字段","值")
查询: esBookRepository.search( 条件 )
返回值: Page,容器,可以直接遍历获取数据
package com.czxy.test;
import com.czxy.TestApplication;
import com.czxy.repository.ESBookRepository;
import com.czxy.vo.ESBook;
import org.elasticsearch.index.query.BoolQueryBuilder;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.search.sort.SortBuilders;
import org.elasticsearch.search.sort.SortOrder;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.elasticsearch.core.query.NativeSearchQueryBuilder;
import org.springframework.test.context.junit4.SpringRunner;
import javax.annotation.Resource;
/**
* @Author Pole丶逐
* @Date 2020/4/14 15:55
* @E-mail
*/
@RunWith(SpringRunner.class)
@SpringBootTest(classes = TestApplication.class)
public class TestData {
@Resource
private ESBookRepository esBookRepository;
@Test
public void test1(){
//创建条件构造器器
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
//把条件查询match放到查询条件中
queryBuilder.withQuery(QueryBuilders.matchQuery("title","简史"));
//创建构造对象并查询
Page<ESBook> page = esBookRepository.search(queryBuilder.build());
System.out.println("总条数: " + page.getTotalElements());
System.out.println("总页数: " + page.getTotalPages());
for (ESBook esBook : page) {
System.out.println(esBook);
}
}
}
5.3.2 多条件查询: bool -- must/mustNot(交集)
多条件拼凑: BoolQueryBuilder对象
- QueryBuilders.boolQuery()
并集操作: must()/mustNot()
@Test
public void test2(){
// 创建条件查询构建器
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
// 获得bool查询条件
BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery();
// 拼接查询条件
boolQueryBuilder.must(QueryBuilders.matchQuery("title","简史"));
boolQueryBuilder.mustNot(QueryBuilders.matchQuery("title","时间"));
// 把条件放入查询条件中
queryBuilder.withQuery(boolQueryBuilder);
// 构建对象并查询
Page<ESBook> page = esBookRepository.search(queryBuilder.build());
// 循环遍历
page.forEach( esBook -> {
System.out.println(esBook);
});
}
5.3.3 多条件查询: bool -- should (并集)
交集操作: boolQueryBuilder.should()
@Test
public void test3(){
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery();
boolQueryBuilder.should(QueryBuilders.matchQuery("title","人类"));
boolQueryBuilder.should(QueryBuilders.matchQuery("title","简史"));
queryBuilder.withQuery(boolQueryBuilder);
Page<ESBook> page = esBookRepository.search(queryBuilder.build());
page.forEach( esBook -> {
System.out.println(esBook);
});
}
5.3.4 精准查询: term
精准查询: QueryBuilders.termQuery( 字段,值 )
@Test
public void test4(){
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
queryBuilder.withQuery(QueryBuilders.termQuery("title","简史"));
Page<ESBook> page = esBookRepository.search(queryBuilder.build());
page.forEach(esBook -> {
System.out.println(esBook);
});
}
5.3.5 区间查询: range
区间查询: QueryBuilders.rangeQuery( 字段 )
- lt(): 小于
- lte(): 小于等于
- gt(): 大于
- gte(): 大于等于
@Test
public void test5(){
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
queryBuilder.withQuery(QueryBuilders.rangeQuery("price").gte(35.5).lte(40.0));
Page<ESBook> page = esBookRepository.search(queryBuilder.build());
page.forEach(esBook -> {
System.out.println(esBook);
});
}
5.3.6 分页查询:
分页查询: queryBuilder.withPageable()
- 分页工具类: PageRequest.of(pageNum,pageSIze)
@Test
public void test6(){
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
queryBuilder.withPageable(PageRequest.of(1,2));
Page<ESBook> page = esBookRepository.search(queryBuilder.build());
page.forEach(esBook -> {
System.out.println(esBook);
});
}
5.3.7 排序查询:
排序查询: queryBuilder.withSort()
- 排序工具类: SortBuilders.fieldSort(排序字段)
- 排序方式: order(SortOrder.DESC | SortOrder.ASC)
@Test
public void test7(){
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
queryBuilder.withSort(SortBuilders.fieldSort("price").order(SortOrder.DESC));
Page<ESBook> page = esBookRepository.search(queryBuilder.build());
page.forEach(esBook -> {
System.out.println(esBook);
});
}
6. 总结
- 查询条件构造器: NativeSearchQueryBuilder
- 查询条件: queryBuilder.withQuery()
- 分页条件: queryBuilder.withPageable()
- 排序条件: queryBuilder.withSort()
- 构造: build()
- 查询条件,通过工具类QueryBuilders 获得
- 关键字查询: matchQuery(字段,值)
- 多条件查询: boolQuery()
- 必须有: must()
- 必须没有; mustNot()
- 并集: should()
- 精准查询: termQuery(字段,值)
- 区间查询: rangeQuery(字段)
- 大于: gt()
- 大于等于: gte()
- 小于: lt()
- 小于等于: lte()
- 分页条件: 工具类PageRequest
- 设置分页参数: PageRequest.of(pageNum,pageSize)
- 排序字段,通过工具类SortBuilders
- 排序字段: SortBuilders.fieldSort("字段")
- 排序方式: order(SortOrder.DESC | SortOrder.ASC)
- 查询结果: Page对象
- 总条数: getTotalElements()
- 总页数: getTotalPages()
- 第几页: getNumber()
- 每页个数: getSize()
- 过得内容: getContent()
- Page 对象可以直接遍历
以上是 02.ElasticSearch(SpringDataElasticSearch) 的全部内容, 来源链接: utcz.com/z/515474.html