简介
Solr 是一个基于 Apache Lucene 构建的开源搜索平台。它提供了强大的搜索功能、高效的索引机制和丰富的配置选项,使得开发者能够轻松构建高性能的搜索应用。
Solr 具有易于使用的 Web 管理界面,方便进行配置和监控。它支持多种数据格式的索引和搜索,能够处理大量的数据,并提供了诸如分页、排序、过滤、高亮显示搜索结果等功能。
有了 MySQL 还有必要用 Solr 吗
即使已经使用了 MySQL 这样的关系型数据库,在某些情况下使用 Solr 仍然是有必要的。
MySQL 擅长处理结构化数据的存储和事务操作,但在搜索功能方面存在一些局限性。例如,对于复杂的全文搜索、模糊搜索、相关性排序等需求,MySQL 可能无法提供高效和灵活的解决方案。
而 Solr 专门为搜索进行了优化,能够快速处理大规模的文本数据搜索,并提供更精确的搜索结果排序和相关性计算。
举例来说,如果您的应用需要快速搜索大量的文章内容、产品描述等文本信息,并且对搜索的响应速度和准确性要求较高,那么单独依靠 MySQL 可能无法满足需求,此时结合 Solr 可以显著提升搜索体验。
另外,如果需要实现实时搜索、动态索引更新等功能,Solr 也更具优势。
安装Solr
下载运行
前往solr的官方下载地址:
https://solr.apache.org/downloads.html
Solr 9.x
版本最低运行要求是 Java 11
,我一直使用的是 Java 8
所以这里我将使用 Solr 8.x
作为本次的教程版本。
下载后将其解压会得到如下的目录结构:
打开终端,进入bin
目录中启动Solr服务:
Windows用户则只需要执行下面的命令:
solr start
安装中文分词器
中文具有独特的语言结构和语义表达,不像英文等语言,单词之间通常有明显的空格分隔。如果直接使用 Solr 默认的分词器处理中文文本,可能会将中文拆分成单个的汉字,而不是按照中文的词语进行切分。
前往Maven仓库下载分词依赖:
https://mvnrepository.com/artifact/com.github.magese/ik-analyzer/8.5.0
将下载下来的 ik-analyzer-8.5.0.jar
放入到 solr-8.11.3/server/solr-webapp/webapp/WEB-INF/lib
中
我们在终端使用命令创建一个 core
来测试一下分词器:
./solr create -c ik_core
然后在 solr-8.11.3/server/solr
下可以看到一个名为 ik_core
的目录:
在 conf
目录下编辑 managed-schema
文件并写入以下内容:
<!-- IKAnalyzer-->
<fieldType name="text_ik" class="solr.TextField" autoGeneratePhraseQueries="false">
<analyzer class="org.wltea.analyzer.lucene.IKAnalyzer" type="index">
</analyzer>
<analyzer class="org.wltea.analyzer.lucene.IKAnalyzer" type="query">
</analyzer>
</fieldType>
重启Solr服务:
测试分词器
在 Solr Admin
中,也就是solr的web界面,选择我们创建的 ik_core
在 Analysis
中测试分词效果(Analyse Fieldname / FieldType 选择为 text_ik):
集成到SpringBoot
创建SpringBoot项目
SpringBoot项目的创建可以借助IDE完成,这里就不再叙述了。
添加maven依赖
在项目的 pom.xml
中添加新的依赖:
<dependency>
<groupId>org.apache.solr</groupId>
<artifactId>solr-solrj</artifactId>
<version>8.11.3</version>
</dependency>
创建配置
在application.yml
中添加solr的配置信息:
solr:
host: http://127.0.0.1:8983/solr
创建配置类:
import org.apache.solr.client.solrj.SolrClient;
import org.apache.solr.client.solrj.impl.HttpSolrClient;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
public class SolrConfig {
@Value("${solr.host}")
private String solrHost;
@Bean
public SolrClient solrClient() {
return new HttpSolrClient.Builder(solrHost).build();
}
}
创建文档索引
在查询数据之前,我们需要在solr中导入我们的数据,并建立索引。
第一种方式来添加文档比较简单:
@Resource
private SolrClient solrClient;
public void indexQuestion() throws Exception{
// 创建一个文档对象
SolrInputDocument inputDocument = new SolrInputDocument();
// 添加字段
inputDocument.addField("id", "1");
inputDocument.addField("name", "名称1");
inputDocument.addField("content", "内容1");
inputDocument.addField("category", "类别1");
// 将文档写入索引库中
solrServer.add("ik_core", inputDocument);
// 提交
solrServer.commit("ik_core");
}
第二种方式则是实用Java Bean的方式,其字段属性使用Solr提供的的 @Field
注解标柱:
@Data
public class Document {
@Field
private String id;
@Field
private String name;
@Field
private String content;
@Field
private String category;
}
然后实例化Bean,并将其添加到我们创建的 ik_core
中进行索引:
@Resource
private SolrClient solrClient;
public boolean indexQuestion() throws SolrServerException, IOException {
// 实例化并添加 Document 对象
Document doc1 = new Document();
doc1.setId("1");
doc1.setName("国内新能源汽车销量持续攀升");
doc1.setContent("今年以来,国内新能源汽车市场表现强劲,销量不断增长。各大厂商纷纷推出新款车型,技术创新不断。");
doc1.setCategory("汽车");
solrClient.addBean("ik_core", doc1);
Document doc2 = new Document();
doc2.setId("2");
doc2.setName("国内电商行业发展新趋势");
doc2.setContent("随着数字化转型的加速,国内电商行业呈现出直播带货、社交电商等新趋势,消费者购物方式发生显著变化。");
doc2.setCategory("电商");
solrClient.addBean("ik_core", doc2);
Document doc3 = new Document();
doc3.setId("3");
doc3.setName("国内5G网络建设加速推进");
doc3.setContent("国内5G网络覆盖范围持续扩大,为智能制造、智慧城市等领域的发展提供了有力支撑。");
doc3.setCategory("通信");
solrClient.addBean("ik_core", doc3);
Document doc4 = new Document();
doc4.setId("4");
doc4.setName("国内旅游市场逐渐复苏");
doc4.setContent("在疫情防控形势好转的背景下,国内旅游市场迎来复苏,各地旅游景点游客数量逐步增加。");
doc4.setCategory("旅游");
solrClient.addBean("ik_core", doc4);
Document doc5 = new Document();
doc5.setId("5");
doc5.setName("国内医疗改革取得新进展");
doc5.setContent("近年来,国内医疗改革不断深化,医保政策优化,医疗服务质量得到提升。");
doc5.setCategory("医疗");
solrClient.addBean("ik_core", doc5);
// 提交
UpdateResponse updateResponse = solrClient.commit("ik_core");
return updateResponse != null && updateResponse.getStatus() == 0;
}
当有了这些数据后,我们即可对这些数据进行检索操作,第一次我们写简单点进行查询:
public void query() throws SolrServerException, IOException {
// 创建查询语句
SolrQuery query = new SolrQuery();
// 设置查询条件
query.set("q", "id:1");
// 执行查询
QueryResponse queryResponse = solrClient.query("ik_core", query);
// 取文档列表
SolrDocumentList documentList = queryResponse.getResults();
for (SolrDocument solrDocument : documentList) {
System.out.println("id:"+solrDocument.get("id")+" ");
System.out.println("名称:"+solrDocument.get("name")+" ");
System.out.println("内容:"+solrDocument.get("content")+" ");
System.out.println("类别:"+solrDocument.get("category")+" ");
}
// 也可以反序列化为Java Bean
List<Document> documents = queryResponse.getBeans(Document.class);
for (Document document : documents) {
System.out.println("id:" + document.getId());
System.out.println("名称:" + document.getName());
System.out.println("内容:" + document.getContent());
System.out.println("类别:" + document.getCategory());
}
}
接下来可以构造条件丰富的查询:
public void query() throws Exception {
// 创建查询语句
SolrQuery query = new SolrQuery();
// 设置查询关键字
query.set("q", "国内");
// 按照id降序排列
query.setSort("id", SolrQuery.ORDER.desc);
// 分页条件
query.setStart(0);
query.setRows(2);
// 在指定的字段中进行查询
query.set("df", "name");
// 设置高亮
query.setHighlight(true);
// 设置高亮的字段
query.addHighlightField("name,content");
// 设置高亮的样式
query.setHighlightSimplePre("<font color='red'>");
query.setHighlightSimplePost("</font>");
// 执行查询
QueryResponse queryResponse = solrClient.query("ik_core", query);
// 返回高亮显示结果
Map<String, Map<String, List<String>>> highlighting = queryResponse.getHighlighting();
System.out.println(highlighting);
// 获取文档列表
SolrDocumentList documentList = queryResponse.getResults();
System.out.println("总记录数:" + documentList.getNumFound());
for (SolrDocument solrDocument : documentList) {
System.out.println("id:" + solrDocument.get("id") + " ");
System.out.println("名称:" + solrDocument.get("name") + " ");
System.out.println("内容:" + solrDocument.get("content") + " ");
System.out.println("类别:" + solrDocument.get("category") + " ");
}
}
删除文档则可以使用id字段进行删除:
public void deleteQuestion() throws SolrServerException, IOException {
solrClient.deleteById("ik_core", "1");
// 提交
solrClient.commit("ik_core");
}
总体的来说 Solr 是一款开源的高性能搜索平台,具有强大搜索功能、可扩展性、丰富特性、灵活配置且易于集成,能满足各种复杂搜索和数据管理需求。
评论 (0)