Spring-data ElasticSearch的使用
1.maven坐标的导入
<dependency><groupId>org.elasticsearch</groupId><artifactId>elasticsearch</artifactId><version>2.4.0</version>
</dependency>
<dependency><groupId>org.springframework.data</groupId><artifactId>spring-data-elasticsearch</artifactId><version>2.0.4.RELEASE</version>
</dependency>
2.准备测试类 Article(添加spring data elasticsearch 注解)
@Document : 文档对象(索引信息index,文档类型mapping)
@Id : 文档主键,唯一标识
@Field : 每个文档的域配置
index = FieldIndex.not_analyzed : 不分词
index = FieldIndex.analyzed : 分词
index = FieldIndex.not : 不创建索引
analyzer = “ik” : 指定使用的分词器
store = true : 是否保存
searchAnalyzer = “ik” : 查询所使用的分词器
type = FieldType.String : 指定域的类型
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.FieldIndex;
import org.springframework.data.elasticsearch.annotations.FieldType;@Document(indexName = "blog3", type = "article")
public class Article {@Id@Field(index = FieldIndex.not_analyzed, store = true, type = FieldType.Integer)private Integer id;@Field(index = FieldIndex.analyzed, analyzer = "ik", store = true, searchAnalyzer = "ik", type = FieldType.String)private String title;@Field(index = FieldIndex.analyzed, analyzer = "ik", store = true, searchAnalyzer = "ik", type = FieldType.String)private String content;public Integer getId() {return id;}public void setId(Integer id) {this.id = id;}public String getTitle() {return title;}public void setTitle(String title) {this.title = title;}public String getContent() {return content;}public void setContent(String content) {this.content = content;}@Overridepublic String toString() {return "Article [id=" + id + ", title=" + title + ", content="+ content + "]";}
}
3.spring配置文件配置ElasticSearch
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"xmlns:elasticsearch="http://www.springframework.org/schema/data/elasticsearch"xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsdhttp://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsdhttp://www.springframework.org/schema/data/elasticsearchhttp://www.springframework.org/schema/data/elasticsearch/spring-elasticsearch-1.0.xsd "><!-- 扫描DAO包 自动创建实现 --><elasticsearch:repositories base-package="cn.itcast.dao" /><!-- 扫描Service包 --><context:component-scan base-package="cn.itcast.service" /><!-- 配置elasticsearch 连接 --><elasticsearch:transport-client id="client" cluster-nodes="localhost:9300" /><!-- spring data elasticsearch DAO 必须依赖 elasticsearchTemplate --><bean id="elasticsearchTemplate" class="org.springframework.data.elasticsearch.core.ElasticsearchTemplate"><constructor-arg name="client" ref="client" /></bean></beans>
4.编写dao的spring-data elasticsearch接口
import java.util.List;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.elasticsearch.repository.ElasticsearchRepository;import cn.itcast.domain.Article;public interface ArticleRepository extendsElasticsearchRepository<Article, Integer> {List<Article> findByTitle(String title);Page<Article> findByTitle(String title, Pageable pageable);}
5.常见错误分析
错误一 :
java.lang.NoClassDefFoundError:org/springframework/core/ResolvableTypeProvider
错误原因: 导报冲突
解决: spring 导包版本要一致,提升 spring 依赖版本 4.1.7 提升 4.2.8 (最高)
错误二:
MapperParsingException[No type specified for field [title]]
错误三:
Caused by: java.lang.AbstractMethodError: org.springframework.data.jpa.repos
原因:是spring-data-jpa.jar的版本和spring-data-commons-core.jar的版本不匹配所造成的,spring-data-commons-core.jar的版本过高了.
在发生异常的时候我的版本是:spring-data-jpa-1.0.2.RELEASE.jar和spring-data-commons-core-1.3.0.M1.jar
更改后:spring-data-jpa-1.0.2.RELEASE.jar和spring-data-commons-core-1.1.0.RELEASE.jar (OK)
错误原因: 实体类中未指定域的类型
解决: 在是类的字段中添加注解@Field(type = FieldType.String)
问题四:
ElasticSearch使用的是jackson来进行对象序列化的,所以有些时候可能会造成双向关联的对象,在转json的时候,会相互引用,造成栈内存溢出,需要使用@JsonIgnore来排除双向引用的字段
6.原始Elasticsearch用法
import java.io.IOException;
import java.net.InetAddress;
import java.util.Iterator;
import java.util.Map;
import java.util.concurrent.ExecutionException;
import org.elasticsearch.action.admin.indices.mapping.put.PutMappingRequest;
import org.elasticsearch.action.delete.DeleteRequest;
import org.elasticsearch.action.search.SearchRequestBuilder;
import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.client.Client;
import org.elasticsearch.client.Requests;
import org.elasticsearch.client.transport.TransportClient;
import org.elasticsearch.common.text.Text;
import org.elasticsearch.common.transport.InetSocketTransportAddress;
import org.elasticsearch.common.xcontent.XContentBuilder;
import org.elasticsearch.common.xcontent.XContentFactory;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.search.SearchHit;
import org.elasticsearch.search.SearchHits;
import org.elasticsearch.search.highlight.HighlightField;
import org.junit.Test;import cn.itcast.elasticsearch.domain.Article;import com.fasterxml.jackson.databind.ObjectMapper;// ElasticSearch 测试程序
public class ElasticSearchTest {@Test// 直接在ElasticSearch中建立文档,自动创建索引public void demo1() throws IOException {// 创建连接搜索服务器对象Client client = TransportClient.builder().build().addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("127.0.0.1"), 9300));// 描述json 数据/** {id:xxx, title:xxx, content:xxx}*/XContentBuilder builder = XContentFactory.jsonBuilder().startObject().field("id", 1).field("title", "ElasticSearch是一个基于Lucene的搜索服务器").field("content","它提供了一个分布式多用户能力的全文搜索引擎,基于RESTful web接口。Elasticsearch是用Java开发的,并作为Apache许可条款下的开放源码发布,是当前流行的企业级搜索引擎。设计用于云计算中,能够达到实时搜索,稳定,可靠,快速,安装使用方便。").endObject();// 建立文档对象client.prepareIndex("blog1", "article", "1").setSource(builder).get();// 关闭连接client.close();}@Test// 搜索在elasticSearch中创建文档对象public void demo2() throws IOException {// 创建连接搜索服务器对象Client client = TransportClient.builder().build().addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("127.0.0.1"), 9300));// 搜索数据// get() === execute().actionGet()SearchResponse searchResponse = client.prepareSearch("blog1").setTypes("article").setQuery(QueryBuilders.matchAllQuery()).get();printSearchResponse(searchResponse);// 关闭连接client.close();}@Test// 各种查询使用public void demo3() throws IOException {// 创建连接搜索服务器对象Client client = TransportClient.builder().build().addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("127.0.0.1"), 9300));// 搜索数据// get() === execute().actionGet()// SearchResponse searchResponse = client.prepareSearch("blog1")// .setTypes("article")// .setQuery(QueryBuilders.queryStringQuery("全面")).get();// SearchResponse searchResponse = client.prepareSearch("blog1")// .setTypes("article")// .setQuery(QueryBuilders.wildcardQuery("content", "*全文*")).get();SearchResponse searchResponse = client.prepareSearch("blog2").setTypes("article").setQuery(QueryBuilders.termQuery("content", "搜索")).get();printSearchResponse(searchResponse);// 关闭连接client.close();}private void printSearchResponse(SearchResponse searchResponse) {SearchHits hits = searchResponse.getHits(); // 获取命中次数,查询结果有多少对象System.out.println("查询结果有:" + hits.getTotalHits() + "条");Iterator<SearchHit> iterator = hits.iterator();while (iterator.hasNext()) {SearchHit searchHit = iterator.next(); // 每个查询对象System.out.println(searchHit.getSourceAsString()); // 获取字符串格式打印System.out.println("title:" + searchHit.getSource().get("title"));}}@Test// 索引操作public void demo4() throws IOException {// 创建连接搜索服务器对象Client client = TransportClient.builder().build().addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("127.0.0.1"), 9300));// 创建索引client.admin().indices().prepareCreate("blog2").get();// 删除索引client.admin().indices().prepareDelete("blog2").get();// 关闭连接client.close();}@Test// 映射操作public void demo5() throws IOException, InterruptedException,ExecutionException {// 创建连接搜索服务器对象Client client = TransportClient.builder().build().addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("127.0.0.1"), 9300));// 添加映射XContentBuilder builder = XContentFactory.jsonBuilder().startObject().startObject("article").startObject("properties").startObject("id").field("type", "integer").field("store", "yes").endObject().startObject("title").field("type", "string").field("store", "yes").field("analyzer", "ik").endObject().startObject("content").field("type", "string").field("store", "yes").field("analyzer", "ik").endObject().endObject().endObject().endObject();PutMappingRequest mapping = Requests.putMappingRequest("blog2").type("article").source(builder);client.admin().indices().putMapping(mapping).get();// 关闭连接client.close();}@Test// 文档相关操作public void demo6() throws IOException, InterruptedException,ExecutionException {// 创建连接搜索服务器对象Client client = TransportClient.builder().build().addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("127.0.0.1"), 9300));// 描述json 数据/** {id:xxx, title:xxx, content:xxx}*/Article article = new Article();article.setId(2);article.setTitle("搜索工作其实很快乐");article.setContent("我们希望我们的搜索解决方案要快,我们希望有一个零配置和一个完全免费的搜索模式,我们希望能够简单地使用JSON通过HTTP的索引数据,我们希望我们的搜索服务器始终可用,我们希望能够一台开始并扩展到数百,我们要实时搜索,我们要简单的多租户,我们希望建立一个云的解决方案。Elasticsearch旨在解决所有这些问题和更多的问题。");ObjectMapper objectMapper = new ObjectMapper();// 建立文档// client.prepareIndex("blog2", "article", article.getId().toString())// .setSource(objectMapper.writeValueAsString(article)).get();// 修改文档// client.prepareUpdate("blog2", "article", article.getId().toString())// .setDoc(objectMapper.writeValueAsString(article)).get();// 修改文档// client.update(// new UpdateRequest("blog2", "article", article.getId()// .toString()).doc(objectMapper// .writeValueAsString(article))).get();// 删除文档// client.prepareDelete("blog2", "article", article.getId().toString())// .get();// 删除文档client.delete(new DeleteRequest("blog2", "article", article.getId().toString())).get();// 关闭连接client.close();}@Test// 批量查询100条记录public void demo7() throws IOException, InterruptedException,ExecutionException {// 创建连接搜索服务器对象Client client = TransportClient.builder().build().addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("127.0.0.1"), 9300));ObjectMapper objectMapper = new ObjectMapper();for (int i = 1; i <= 100; i++) {// 描述json 数据Article article = new Article();article.setId(i);article.setTitle(i + "搜索工作其实很快乐");article.setContent(i+ "我们希望我们的搜索解决方案要快,我们希望有一个零配置和一个完全免费的搜索模式,我们希望能够简单地使用JSON通过HTTP的索引数据,我们希望我们的搜索服务器始终可用,我们希望能够一台开始并扩展到数百,我们要实时搜索,我们要简单的多租户,我们希望建立一个云的解决方案。Elasticsearch旨在解决所有这些问题和更多的问题。");// 建立文档client.prepareIndex("blog2", "article", article.getId().toString()).setSource(objectMapper.writeValueAsString(article)).get();}// 关闭连接client.close();}@Test// 分页搜索public void demo8() throws IOException {// 创建连接搜索服务器对象Client client = TransportClient.builder().build().addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("127.0.0.1"), 9300));// 搜索数据// get() === execute().actionGet()SearchRequestBuilder searchRequestBuilder = client.prepareSearch("blog2").setTypes("article").setQuery(QueryBuilders.matchAllQuery());// 查询第2页数据,每页20条searchRequestBuilder.setFrom(20).setSize(20);SearchResponse searchResponse = searchRequestBuilder.get();printSearchResponse(searchResponse);// 关闭连接client.close();}@Test// 高亮查询结果 处理 搜索public void demo9() throws IOException {// 创建连接搜索服务器对象Client client = TransportClient.builder().build().addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("127.0.0.1"), 9300));ObjectMapper objectMapper = new ObjectMapper();// 搜索数据SearchRequestBuilder searchRequestBuilder = client.prepareSearch("blog2").setTypes("article").setQuery(QueryBuilders.termQuery("title", "搜索"));// 高亮定义searchRequestBuilder.addHighlightedField("title"); // 对title字段进行高亮searchRequestBuilder.setHighlighterPreTags("<em>"); // 前置元素searchRequestBuilder.setHighlighterPostTags("</em>");// 后置元素SearchResponse searchResponse = searchRequestBuilder.get();SearchHits hits = searchResponse.getHits(); // 获取命中次数,查询结果有多少对象System.out.println("查询结果有:" + hits.getTotalHits() + "条");Iterator<SearchHit> iterator = hits.iterator();while (iterator.hasNext()) {SearchHit searchHit = iterator.next(); // 每个查询对象// 将高亮处理后内容,替换原有内容 (原有内容,可能会出现显示不全 )Map<String, HighlightField> highlightFields = searchHit.getHighlightFields();HighlightField titleField = highlightFields.get("title");// 获取到原有内容中 每个高亮显示 集中位置 fragment 就是高亮片段Text[] fragments = titleField.fragments();String title = "";for (Text text : fragments) {title += text;}// 将查询结果转换为对象Article article = objectMapper.readValue(searchHit.getSourceAsString(), Article.class);// 用高亮后内容,替换原有内容article.setTitle(title);System.out.println(article);}// 关闭连接client.close();}
}
7.使用Spring data ElasticSearch来操作索引库
(1)扫描jpa包
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"xmlns:elasticsearch="http://www.springframework.org/schema/data/elasticsearch"xsi:schemaLocation="http://www.springframework.org/schema/data/elasticsearch http://www.springframework.org/schema/data/elasticsearch/spring-elasticsearch-1.0.xsdhttp://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsdhttp://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"><!-- 扫描DAO包 自动创建实现 --> <elasticsearch:repositories base-package="cn.itcast.bos.index" /><!-- 配置elasticsearch 连接 --> <elasticsearch:transport-client id="client"cluster-nodes="localhost:9300" /> <!-- spring data elasticsearch DAO 必须依赖 elasticsearchTemplate --><bean id="elasticsearchTemplate"class="org.springframework.data.elasticsearch.core.ElasticsearchTemplate"><constructor-arg name="client" ref="client" /> </bean> </beans>
(2)继承Repository接口
import org.springframework.data.elasticsearch.repository.ElasticsearchRepository;
import cn.itcast.bos.domain.delivery.WayBill;public interface WayBillIndexRepository extends ElasticsearchRepository<WayBill, Integer> {}
测试(添加)
// 执行保存索引库
wayBillIndexRepository.save(entity);
测试(条件分页查询)
/*** 分页查询索引库*/@Overridepublic void findPage(WayBill wayBill, PageBean pageBean) {BoolQueryBuilder query = new BoolQueryBuilder();if (StringUtils.isNotBlank(wayBill.getWayBillNum())) {// 设置运单号条件QueryBuilder termQuery = new TermQueryBuilder("wayBillNum", wayBill.getWayBillNum());query.must(termQuery);}if (StringUtils.isNotBlank(wayBill.getSendAddress())) {// 设置发送地址条件BoolQueryBuilder boolQuery = new BoolQueryBuilder();QueryBuilder wildcardQuery = new WildcardQueryBuilder("sendAddress", "*" + wayBill.getSendAddress() + "*");QueryBuilder queryStringQuery = new QueryStringQueryBuilder(wayBill.getSendAddress()).field("sendAddress").defaultOperator(Operator.AND);boolQuery.should(wildcardQuery);boolQuery.should(queryStringQuery);query.must(boolQuery);}if (StringUtils.isNotBlank(wayBill.getRecAddress())) {// 设置接收地址条件BoolQueryBuilder boolQuery = new BoolQueryBuilder();QueryBuilder wildcardQuery = new WildcardQueryBuilder("recAddress", "*" + wayBill.getRecAddress() + "*");QueryBuilder queryStringQuery = new QueryStringQueryBuilder(wayBill.getRecAddress()).field("recAddress").defaultOperator(Operator.AND);boolQuery.should(wildcardQuery);boolQuery.should(queryStringQuery);query.must(boolQuery);}if (StringUtils.isNotBlank(wayBill.getSendProNum())) {// 设置产品类型条件QueryBuilder termQuery = new TermQueryBuilder("sendProNum", wayBill.getSendProNum());query.must(termQuery);}if (wayBill.getSignStatus() != null && wayBill.getSignStatus() != 0) {// 设置快递产品类型编号条件QueryBuilder termQuery = new TermQueryBuilder("signStatus", wayBill.getSignStatus());query.must(termQuery);}Page<WayBill> search = wayBillIndexRepository.search(query,new PageRequest(pageBean.getCurrentPage() - 1, pageBean.getPageSize()));pageBean.setRows(search.getContent());pageBean.setTotal(search.getTotalElements());}
Spring-data ElasticSearch的使用相关推荐
- Spring data elasticsearch的使用
Spring data elasticsearch的使用 ArticleService package cn.zxl.service;import java.util.List;import org. ...
- Spring Data ElasticSearch入门案例
Spring Data ElasticSearch入门案例 创建maven工程elasticsearch_springdata 基于maven导入坐标 导入spring data elasticsea ...
- spring data elasticsearch 对应 elasticsearch 版本
spring data elasticsearch elasticsearch 3.2.x 6.5.0 3.1.x 6.2.2 3.0.x 5.5.0 2.1.x 2.4.0 2.0.x 2.2.0 ...
- Spring Data Elasticsearch案例详解
一.Elasticsearch 工作原理 1.1 文档存储的路由 当索引到一个文档(如:报价系统),具体的文档数据(如:报价数据)会存储到一个分片.具体文档数据会被切分,并分别存储在分片 1 或者 分 ...
- Spring Boot + Spring Data + Elasticsearch实例
在本文中,我们将讨论"如何创建Spring Boot + Spring Data + Elasticsearch范例". 本文中使用的工具: Spring Boot 1.5.1.R ...
- Elasticsearch 实战1:ES 项目实战(一)Java 集成 Spring Data Elasticsearch(一):简介及环境搭建
一:前语 1.项目文档 CSDN 专栏:<Elasticsearch 入门和项目实战> 博客路径: https://blog.csdn.net/a767815662/category_91 ...
- 【Spring Data ElasticSearch】高级查询,聚合
[Spring Data ElasticSearch]高级查询,聚合 1. 高级查询 1.1 基本查询 1.2 自定义查询 1.3 分页查询 1.4 排序 2. 聚合 2.1 聚合为桶 2.2 嵌套聚 ...
- Spring系列学习之Spring Data Elasticsearch数据访问
英文原文:https://spring.io/projects/spring-data-elasticsearch 目录 概述 特性 快速开始 学习 文档 概述 Elasticsearch的Sprin ...
- Spring Data Elasticsearch 和 x-pack 用户名/密码验证连接
为什么80%的码农都做不了架构师?>>> 使用Spring Data Elasticsearch连接elasticsearch时,正常情况下只需要在application.pr ...
- Lucene 和 Kibana、ElasticSeach、Spring Data ElasticSearch
什么是全文检索 数据分类 生活中的数据总体分为两种:结构化数据和非结构化数据. 结构化数据 - 行数据,可以用二维表结构来逻辑表达实现的数据:指具有固定格式或有限长度的数据,如数据库,元数据等. 非结 ...
最新文章
- exe编辑器_windows下的EXE文件大揭密
- 20行Python代码说清“量子霸权”
- 增加XP的IIS连接数,解决403.9连接用户过多的问题
- Linux从零开始(二、基础命令(续二)解压 tar)
- 【转载】查看MSSQL数据库每个表占用的空间大小的方法
- 账户配置阻止使用计算机.怎样开机,开机自启动设置怎么操作 开机自启动设置如何禁止【图文介绍】...
- java高并发日志_高并发下log4j的性能瓶颈
- 学生宿舍管理项目开发计划书_第六组学生宿舍管理系统项目计划书
- Axure 基本功能
- 关于海康门禁的开发体会一
- 目前我国网络安全人才市场状况
- 上传Android library到JitPack
- 华硕笔记本进bios按哪个键 华硕手提电脑怎么进bios设置
- 第39级台阶--递归
- Mysql将txt文件导入数据库采坑 load data local infile
- DTAS 国产三维尺寸公差分析软件尺寸链计算几何数据导入应用
- 30个很棒的jQuery幻灯片放映插件
- iOS开发之去除图片白色背景
- windows添加右键点击打开CMD(运行)的方法
- ping请求超时的解决方法?
热门文章
- java 自定义表单 动态表单 表单设计器 工作流引擎 flowable 设计方案
- mybatis实现代码自动生成
- spring boot 访问zul页面语言设置
- 在VC下实现串口通讯
- 批量doc转docx方法,使用软件、插件
- android通讯录加密,一种手机通讯录加解密方式
- 网络安全05_VMware 虚拟机软件安装_准备Kali- Linux虚拟机_Windows Server 2003 Enterprise 虚拟机下载和安装
- 老罗Android开发视频教程_基于JavaSE开发(适合Android初学者菜鸟级别的人)
- 暴风影音2009 Real插件无法下载安装问题解决
- pythonjson格式化输出_pythonjson格式化输出_Python json格式化打印实现过程解析