一.Solr基础回顾

1.什么是solr

为了在CNET 公司网站上添加搜索功能,Yonik Seely于2004年创建了Solr。并在2006年1月,它成为 Apache软件基金会下的一个开源项目。并于2016年发布新版本Solr 6.0,支持并行SQL查询的执行,目前最新的版本是9.5。 Solr是一个开源搜索平台,用于构建搜索应用程序。 它建立在Lucene(全文搜索库)之上。Solr不仅限于 搜索,也可以用于存储目的。像其他NoSQL数据库一样,它是一种非关系数据存储和处理技术。 Solr是一个企业级的 ,快速的 ,可扩展的,可部署的,搜索和存储引擎,用于优化搜索大量以文本为 中心的数据。

2.Solr和Lucene的区别

Lucene是一个开放源代码的全文检索工具包,它不是一个完整的全文检索应用。Lucene仅提供了完整 的查询引擎和索引引擎 仍然需要关注数据获取、解析、索引查看等方面的东西。Lucene的目的是为软 件开发人员提供一个简单易用的工具包,以方便的在目标系统中实现全文检索的功能,或者以Lucene 为基础构建全文检索应用。 Solr的目标是打造一款企业级的搜索引擎系统,它是基于Lucene一个搜索引擎服务,可以独立运行, 通过Solr可以非常快速的构建企业的搜索引擎,通过Solr也可以高效的完成站内搜索功能。 优势:

1、solr是已经将整个索引操作功能封装好了的搜索引擎系统(企业级搜索引擎产品)

2、solr可以部署到单独的服务器上(WEB服务)提供服务,我们的业务系统就只要发送请求,接收响应即可,降低了业务系统的负载并且solr的索引库就不会受业务系统服务器存储空间的限制

3、solr支持分布式集群,索引服务的容量和能力可以线性扩展 

3.Solr 的核心特性

1.先进的全文搜索功能

2.基于标准的开放接口,Solr搜索服务器支持通过XML、JSON和HTTP查询和获取结果。

3.高度可扩展和容错,能够有效地复制到另外一个Solr搜索服务器

4.Solr可以通过HTML页面管理,使用XML配置达到灵活性和适配性

5.灵活的插件体系 新功能能够以插件的形式方便的添加到Solr服务器上。

6.强大的数据导入功能 数据库和其他结构化数据源现在都可以导入、映射和转化。

4.Solr 的安装方式

方式一

1.下载solr项目包 或者上传压缩包到服务器

直接去官网下载 https://lucene.apache.org/solr/downloads.html 或者 wget https://mirror.bit.edu.cn/apache/lucene/solr/7.7.3/solr-7.7.3.tgz

2.解压

tar -xvf solr-7.7.3.tgz

3.启动solr,到solr7.7.3/bin下

./solr start -force -port 端口 默认端口 8983

4.使用浏览器访问

  http://localhost:8983   

5.配置solr_core 在server/solr 下建立一个文件夹名字任意这里叫 new_core

/root/solr/solr-7.7.3/server/solr/configsets/_default/conf 到 server/solr/new_core cp /root/solr/solr-7.7.3/server/solr/configsets/_default/conf -rf new_core 修改 managed-schema 为 schema.xml mv managed-schema schema.xml

方式二

Solr 解压后server/solr-webapp下一个webapp目录,它就是Solr的Web项目,把它复制到 tomcat的webapps目录下并改名为solr

# 进入Solr的server目录下    
cd /root/solr/solr-7.7.3/server/solr-webapp/   
 # 复制webapp目录到tomcat-solr的webapps目录下    
cp -r webapp/ /root/solr/apache-tomcat-8.0.52/webapps    
# 将Solr的web应用改名    
cd /root/solr/apache-tomcat-8.0.52/webapps   
 # 将webapp重命名为solr    
mv webapp solr 
#复制所需依赖jar包  
#复制solr-7.7.3\server\lib\ext 下的jar包到apache-tomcat-8.0.52\webapps\solr\WEBINF\lib下(即刚刚复制并重命名为solr的文件夹下)    
cp ext/ /root/solr/apache-tomcat-8.0.52/webapps/solr/WEB-INF/lib/    
#复制solr-7.7.3\server\lib下所有metrics-开头的jar包(一共有5个)到apache-tomcat-    8.0.5/webapps/solr/WEB-INF/lib/    
cp metrics- /root/solr/apache-tomcat-8.0.52/webapps/solr/WEB-INF/lib/  
#配置solrhome    这个目录用于存储Solr Core的数据及配置文件    首先创建solrhome存储Solr索引文件    mkdir -p /usr/local/solr/solrhome    复制server/solr目录下所有内容到solrhome   
cp -r * /usr/local/solr/solrhome/  
 
#配置Tomcat    修改web.xml    修改复制到tomcat中的Solr项目中的 WEB-INF 目录下的 web.xml 配置文件    修改 solr_home 路径指向我们刚刚创建的 solrhome  
vim web.xml

~~~xml      solr/home /usr/local/solr/solrhome java.lang.String     ~~~
去掉安全认证  
~~~xml         ~~~
 启动tomcat 访问测试    修改tomcat的执行权限 然后启动    chmod 777 -R bin    ./bin/startup.sh    在浏览器上访问solr    http://IP:端口/solr/index.html  
 
 配置solr_core    /root/solr/solr-7.7.3/server/solr/configsets/_default/conf 到 solrhome/new_core    cp /root/solr/solr-7.7.3/server/solr/configsets/_default/conf -rf new_core    修改 managed-schema 为 schema.xml    mv managed-schema schema.xml

一、下载与安装:

  1. 下载:solr.apache.org/downloads.html 到官网点击Download下载。

Solr入门_analyzer

  1. 下载完成后会得到一个压缩包,解压后会获得一个solr-9.5文件夹,此文件夹目录结构如下图

Solr入门_solr_02

二、运行solr

Solr的运行分为单机运行和集群运行,这里以单机为例:

  1. 在bin目录下执行bin/solr start 此命令会启动solr应用服务器默认端口为8983,如果想指定端口号启动可以加参数–p例 如:solr start –p 8888.


Solr入门_analyzer_03


如图这句提示出现后证明服务启动成功(启动过程中如果打印java异常堆栈log4j2.xml 文件名、目录名或卷标语法不正确。没有关系不妨碍我们正常使用solr可以忽略此问题),接下来在浏览器输入http://localhost:8888/solr可以进入Admin UI界面验证是否启动成功如下图


Solr入门_analyzer_04

此界面是用来管理solr的,此时solr服务器已经可以启动成功啦下面介绍一下其他比较常用的solr命令。

  1. solr常用命令:

solr start –p 端口号 单机版启动solr服务

solr restart –p 端口号 重启solr服务

solr stop –p 端口号关闭solr服务

solr create –c name 创建一个core实例(core概念后面介绍)

此外有关于solr集群版启动方式和其他更多的命令可以参看官方文档https://lucene.apache.org/solr/guide/7_4/solr-control-script-reference.html

5.创建core实例:

  1. core简介:简单说core就是solr的一个实例,一个solr服务下可以有多个core,每个core下都有自己的索引库和与之相应的配置文件,所以在操作solr创建索引之前要创建一个core,因为索引都存在core下面。
  2. core创建:core的创建方式有很多种一下列出两种比较方便的。

(1) 在bin目录下执行solr create –c name,创建一个core,默认创建出来的位置如下图

Solr入门_solr_05


(2) 第二种方式是直接使用AdminUI页面创建一个core,如下图

Solr入门_analyzer_06

点击【add Core】按钮,提示:

Solr入门_分词器_07

Error CREATEing SolrCore 'e-commerce': Unable to create core [e-commerce] Caused by: Can't find resource 'solrconfig.xml' in classpath or 'D:\server\solr\server\solr\e-commerce'

我们需要在server/solr/configsets/_default中的conf文件夹,复制到server/solr/e-commerce文件中。

在点击【Add Core】按钮,就可以新建成功了。

Solr入门_分词器_08

6. 配置schema

1.schema简介:

schema是用来告诉solr如何建立索引的,他的配置围绕着一个schema配置文件,这个配置文件决定着solr如何建立索引,每个字段的数据类型,分词方式等,老版本的schema配置文件的名字叫做schema.xml他的配置方式就是手工编辑,但是现在新版本的schema配置文件的名字叫做managed-schema,他的配置方式不再是用手工编辑而是使用schemaAPI来配置,官方给出的解释是使用schemaAPI修改managed-schema内容后不需要重新加载core或者重启solr更适合在生产环境下维护,如果使用手工编辑的方式更改配置不进行重加载core有可能会造成配置丢失,配置文件所在的路径如下图:

Solr入门_analyzer_09

2.schema主要成员:

(1) fieldType:为field定义类型,最主要作用是定义分词器,分词器决定着如何从文档中检索关键字。

(2) analyzer:他是fieldType下的子元素,这就是传说中的分词器,他由一组tokenizer和filter组成,如下图所示


<!-- A text type for English text where stopwords and synonyms are managed using the REST API -->
    <fieldType name="managed_en" class="solr.TextField" positionIncrementGap="100">
      <analyzer type="index">
        <tokenizer name="standard"/>
        <filter name="managedStop" managed="english" />
        <filter name="managedSynonymGraph" managed="english" />
        <filter name="flattenGraph"/>
      </analyzer>
      <analyzer type="query">
        <tokenizer name="standard"/>
        <filter name="managedStop" managed="english" />
        <filter name="managedSynonymGraph" managed="english" />
      </analyzer>
    </fieldType>

(3) field:他是创建索引用的字段,如果想要这个字段生成索引需要配置他的indexed属性为true,stored属性为true表示存储该索引。如下图所示每个field都要引用一种fieldType由type属性定义

<field name="text" type="text_general" indexed="true" stored="false" multiValued="true"/>

这里描述的只是最常用的三个元素,关于更多schema的介绍请参考http://lucene.apache.org/solr/guide/7_4/documents-fields-and-schema-design.html

3.Schema API:

Schema API其实就是用post请求向solr服务器发送携带json参数的请求,所有操作内容都封装在json中,如果是linux系统直接使用curl工具,如果是windows系统推荐使用ApiFox


Solr入门_solr_10

这里以添加一个field为例,下面列出其他API:

add-field: add a new field with parameters youprovide.

delete-field: delete a field.

replace-field: replace an existing field withone that is differently configured.

观看更多API内容请参考Apache Solr Reference Guide :: Apache Solr Reference Guide

7.中文分词器:

solr7自带分词中文分词器

1、复制jar包

cp contrib/analysis-extras/lucene-libs/lucene-analyzers-smartcn-7.7.3.jar
solr/WEB-INF/lib

2.复制新项目的配置文件

创建solrcore mkdir solrhome/new_core
cp -r server/solr/configsets/_default/conf solrhome/new_core/

3.然后到solrhome/new_core/conf目录中打开managed-schema文件,增加如下代码

<fieldType name="text_hmm_chinese" class="solr.TextField"
positionIncrementGap="100">
<analyzer type="index">
<tokenizer
class="org.apache.lucene.analysis.cn.smart.HMMChineseTokenizerFactory"/>
</analyzer>
<analyzer type="query">
<tokenizer
class="org.apache.lucene.analysis.cn.smart.HMMChineseTokenizerFactory"/>
</analyzer>
</fieldType>

IK中文分词器

方式一

1.下载分词器

一般解决分词问题会选择ikanalyzer,因为相对来说ikanalyzer更新的比较的好, solr7 本身提供中文 的分词jar包,在此一并讲一下 下载solr7版本的ik分词器,下载地址:http://search.maven.org/#search%7Cga%7C1%7Ccom.github.magese 分词器GitHub源码地址:https://github.com/magese/ik-analyzer-solr7 将下载好的jar包放入 tomcat 对应的项目的 /WEB-INF/lib目录中

2、复制新项目的配置文件

创建solrcore mkdir solrhome/ik cp -r server/solr/configsets/_default/conf solrhome/ik/

3.然后到server/solr/ik/conf目录中打开managed-schema文件,增加如下代码

<!-- ik分词器 -->
    <fieldType name="text_ik" class="solr.TextField">
        <analyzer type="index">
            <tokenizer class="org.wltea.analyzer.lucene.IKTokenizerFactory" useSmart="false" conf="ik.conf"/>
            <filter class="solr.LowerCaseFilterFactory"/>
        </analyzer>
        <analyzer type="query">
            <tokenizer class="org.wltea.analyzer.lucene.IKTokenizerFactory" useSmart="true" conf="ik.conf"/>
            <filter class="solr.LowerCaseFilterFactory"/>
        </analyzer>


    </fieldType>

使用停用词和同义词

<!-- ik分词器 -->
    <fieldType name="text_ik" class="solr.TextField">
        <analyzer type="index">
            <tokenizer class="org.wltea.analyzer.lucene.IKTokenizerFactory" useSmart="false" conf="ik.conf"/>
            <filter class="solr.LowerCaseFilterFactory"/>
      <filter class="solr.StopFilterFactory" words="stopwords.txt"/>
        </analyzer>
        <analyzer type="query">
            <tokenizer class="org.wltea.analyzer.lucene.IKTokenizerFactory" useSmart="true" conf="ik.conf"/>
            <filter class="solr.LowerCaseFilterFactory"/>
      <filter class="solr.StopFilterFactory" words="stopwords.txt"/>
        </analyzer>
    </fieldType>
  • words属性指定停用词文件的绝对路径或相对solr主目录下conf/目录的相对路径
  • 停用词定义语法:一行一个

stopwords.txt

hello
like

同义词

<analyzer type="index">
<tokenizer class="solr.StandardTokenizerFactory"/>
<filter class="solr.SynonymGraphFilterFactory" synonyms="mysynonyms.txt"/>
<filter class="solr.FlattenGraphFilterFactory"/>
</analyzer>
<analyzer type="query">
<tokenizer class="solr.StandardTokenizerFactory"/>
<filter class="solr.SynonymGraphFilterFactory" synonyms="mysynonyms.txt"/>
</analyzer>

mysynonyms.txt synonyms属性指定同义词文件的绝对路径或相对solr主目录下conf/目录的相对路径 同义词定义语法:一类一行,如下表示,=>表示查询时标准化为后面的内容

couch,sofa,divan
teh => the
huge,ginormous,humungous => large
small => tiny,teeny,weeny
瓷器 => 中国

方式二

solr自带了一些中文分词器,比较好用的是SmartChineseAnalyzer,但是扩展性比较差不能自定义扩展中文词库,所以这里选择使用IKAnalyzer,这是第三方的一个分词器可以很好的扩展中文词库,IKAnalyzer下载后解压会有如下文件


Solr入门_solr_11


把核心jar文件复制到solr WEB应用的lib文件夹下,如下图


Solr入门_analyzer_12


把配置文件和词库等文件复制到WEB应用的classes文件夹下,如果子WEB-INF下没有这个文件夹自己创建即可,如下图:


Solr入门_分词器_13


如果想要扩展词库可以在ext.dic文件中配置自定义的中文词组,例如:诛仙这个词组,这个分词器的算法是算不出来的但是通过我们自定义词库,分词器也可以把诛仙列出关键词。


Solr入门_analyzer_14

上图是ext.dic文件中的内容,注意编辑此文件时字符编码最好是UTF-8无BOM模式,这个可以通过EditPlus等文本编辑工具设置。下面开始在Schema中应用分词器如下图:


Solr入门_analyzer_15


定义了一个text_ik这个字段类型并采用Ik分词器,接下来在field元素定义式指定type=text_ik就可以把这个分词器应用在这个field中。

验证

接下来我们来验证下ik分词器,如下图:


Solr入门_analyzer_16



Solr入门_分词器_17


8.DIH导入索引数据

  1. DIH简介:

DIH全称是Data Import Handler 数据导入处理器,顾名思义这是向solr中导入数据的,我们的solr目的就是为了能让我们的应用程序更快的查询出用户想要的数据,而数据存储在应用中的各种地方入xml、pdf、关系数据库中,那么solr首先就要能够获取这些数据并在这些数据中建立索引来达成快速搜索的目的,这里就列举我们最常用的从关系型数据库中向solr导入索引数据。

  1. 在我们自己建立的core的目录下有conf目录,这里面有着几个很重要的配置文件,之前我们用到的managed-schema(老版本是schema.xml)也在其中,另外还有一个solrconfig.xml文件,这是我们DIH配置的第一步,需要在此文件中配置数据导入文件的映射位置如下图:


Solr入门_solr_18


第二步配置数据导入文件,这个文件可以在solr根目录下的示例文件中copy一份到core/conf目录下,也就是跟solrconfig.xml在一个目录下,因为solrconfig.xml中配置的相对路径就是这里,当然也可以写绝对路径。如下图:


Solr入门_analyzer_19


Copy过去之后这个文件名可以自定义,我就改成了MyDataConfig.xml,下面开始配置如下图:


Solr入门_分词器_20


(1)首先配置数据源关系型数据库基本四项,驱动类,url,用户名,密码。

(2)配置document,可以把它当作与mysql中数据库一个层级的对象。

(3)配置entity,可以把它当作与数据库中一个表对应,在query中书写查询sql。

(4)配置field与表中的字段与之对应。

注意这里容易与schema中的配置混淆,我的理解是schema中配置的是创建索引的配置,而索引的创建需要有数据基础,而现在讲的数据导入文件就是建立索引的数据基础,他是创建索引的元数据。现在配置文件完成后可以用DIH命令执行了。

  1. DIH 命令

DIH命令就是用来执行数据导入的,命令种类繁多这里只列出简单常用。DIH命令采用的方式是URL的方式。

full-import:全部数据导入例如:


Solr入门_analyzer_21


接下来验证下数据是否真的导入成功了,如下图


Solr入门_solr_22


fq:过滤的字段,df:默认查询字段,start,rows:分页配置,sort:排序,更多关于查询语句的介绍请参考http://lucene.apache.org/solr/guide/7_4/searching.html

9、solrJ(java客户端)

简介:solrJ是java访问solr的客户端工具包,solr也提供了其他语言访问的客户端,可以到官方文档查看,现在solr的索引和数据导入都已经有,但是作为项目中应用的一个组件,少不了java与solr的沟通。

1.导入solrJ依赖

如果你是用的是依赖管理工具如maven那么很简单直接添加依赖。

<dependency>
 <groupId>org.apache.solr</groupId>
 <artifactId>solr-solrj</artifactId>
 <version>7.4.0</version>
</dependency>

2. SolrJ的基本操作

增加和修改文档

根据id(唯一约束)域来更新Document的内容,如果根据id值搜索不到id域则会执行添加操作,如果 找到则更新。

private String serverUrl = "http://localhost:8080/solr/ik";

    @Test
    public void testSaveOrUpdateIndex() throws Exception {
        // 创建客户端
        HttpSolrClient client = new HttpSolrClient.Builder(serverUrl).build();
        SolrInputDocument doc = new SolrInputDocument();
        // 添加文档数据
        doc.addField("id", "41");
        doc.addField("name", "java架构师成功之路");
        doc.addField("desc", "Lucene Solr ES java架构师都得学 最重点的是ES");
        doc.addField("price", 12800);
        client.add(doc);
        client.commit();
        client.close();
    }

删除文档

@Test
    public void testDelete() throws Exception {
        // 创建客户端
        HttpSolrClient client = new HttpSolrClient.Builder(serverUrl).build();
        // 根据id 删除
        // client.deleteById("41");
        // 根据查询删除
        client.deleteByQuery("name:solr1");
        client.commit();
        client.close();
    }

查询

@Test
    public void testSimpleQuery() throws Exception {
        // 创建客户端
        HttpSolrClient client = new HttpSolrClient.Builder(serverUrl).build();
        // 创建查询对象
        SolrQuery query = new SolrQuery();
        // 设置查询条件
        query.set("q", "name:*");

        // 执行查询
        QueryResponse queryResponse = client.query(query);
        // 获取文档列表
        SolrDocumentList documentList = queryResponse.getResults();
        for (SolrDocument solrDocument : documentList) {
            System.out.println("id:" + solrDocument.get("id"));
            System.out.println("name:" + solrDocument.get("name"));
            System.out.println("desc:" + solrDocument.get("desc"));
            System.out.println("price:" + solrDocument.get("price"));
        }

        client.close();
    }

3.高级查询

查询参数

查询参数 与 solr管理界面的条件一致
q - 查询字符串,如果查询所有*:* (id:1)
fq - (filter query)过虑查询,过滤条件,基于查询出来的结果
start - 分页开始
rows - 分页查询数据
sort - 排序,格式:sort=<field name>+<desc|asc>[,<field name>+<desc|asc>]… 。
示例:(score desc, price asc)表示先 “score” 降序, 再 “price” 升序,默认是相关性降序。
wt - (writer type)指定输出格式,可以有 xml, json, php, phps。
fl表示索引显示那些field( *表示所有field,如果想查询指定字段用逗号或空格隔开
如:name,price,desc或name price desc 注意:字段是严格区分大小写的
q.op 表示q 中 查询语句的 各条件的逻辑操作 AND(与) OR(或)
hl 是否高亮 ,如hl=true
hl.fl 高亮field ,hl.fl=name,desc
hl.simple.pre 高亮前面的格式
hl.simple.post 高亮后面的格式

检索运算符

1. “:” 指定字段查指定值,如返回所有值*:*
2. “?” 表示单个任意字符的通配
3. “*” 表示多个任意字符的通配(不能在检索的项开始使用*或者?符号)
4. “~” 表示模糊检索 如:so~N 匹配 N 个编辑距离以内的内容。
5. 邻近检索,如检索相隔10个单词的”apache”和”jakarta”,”jakarta apache”~10
6. “^” 控制相关度检索,如检索solr apache,同时希望去让”slor”的相关度更加好,那么在其后加
上”^”符号和增量值,即solr^4 apache
7. 布尔操作符AND、||
8. 布尔操作符OR、&&
9. 布尔操作符NOT、!、- (排除操作符不能单独与项使用构成查询)
10. “+” 存在操作符,要求符号”+”后的项必须在文档相应的域中存在
11. [ ] 包含范围检索,如检索某时间段记录,包含头尾,price:[120 TO 600]

查询和高亮信息获取

@Test
    public void testComplexQuery() throws Exception {
        // 创建客户端
        HttpSolrClient client = new HttpSolrClient.Builder(serverUrl).build();
        SolrQuery query = new SolrQuery();
        query.setQuery("solr");
        // 过滤条件
        query.setFilterQueries("name:solr");
        // 排序
        query.setSort("price", SolrQuery.ORDER.desc);
        // 分页
        query.setStart(0);
        query.setRows(5);
        // 设置返回的域
        query.setFields("id", "name", "price", "desc");
        // 设置默认搜索域
        query.set("df", "desc");
        // 高亮设置
        query.setHighlight(true);
        query.addHighlightField("name desc");
        query.setHighlightSimplePre("<font color='red'>");
        query.setHighlightSimplePost("</font>");
        // 执行查询
        QueryResponse queryResponse = client.query(query);
        SolrDocumentList solrDocumentList = queryResponse.getResults();
        // 打印查询数据量
        System.out.println("查询到的书的数量:" + solrDocumentList.getNumFound());
        // 获取高亮信息
        Map<String, Map<String, List<String>>> bookHL = queryResponse.getHighlighting();
        // 遍历文档数据  显示高亮信息和普通信息
        for (SolrDocument solrDocument : solrDocumentList) {
            // 获取name 对应的 高亮信息
            String nameHL = "";
            List<String> list = bookHL.get(solrDocument.get("id")).get("name");
            // 判断是否有高亮内容
            if (null != list) {
                nameHL = list.get(0);
                System.out.println("nameHL=" + nameHL);
            }

            String descHL = "";
            List<String> list2 = bookHL.get(solrDocument.get("id")).get("desc");
            // 判断是否有高亮内容
            if (null != list2) {
                descHL = list2.get(0);
                System.out.println("descHL=" + descHL);
            }
            System.out.println("id:" + solrDocument.get("id"));
            System.out.println("name:" + solrDocument.get("name"));
            System.out.println("desc:" + solrDocument.get("desc"));
            System.out.println("price:" + solrDocument.get("price"));
        }
        client.close();
    }

10.springboot访问solr

1、Maven依赖

<parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.3.0.RELEASE</version>
    </parent>
    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-solr</artifactId>
        </dependency>
    </dependencies>

2、配置文件

server.port=8081

spring.data.solr.host=http://localhost:8080/solr/ik

11.solrCloud

1.SolrCloud简介

介绍 SolrCloud 是Solr提供的分布式搜索方案,当索引量很大,搜索请求并发很高,这时需要使用 SolrCloud来满足这些需求。当一个系统的索引数据量少的时候是不需要使用SolrCloud的。 SolrCloud是基于Solr和Zookeeper的分布式搜索方案。它的主要思想是使用Zookeeper作为solrCloud集群的配置信息中心,统一管理solrcloud的配置,比如solrconfig.xml和managed-schema。 场景 SolrCloud(solr集群)是Solr提供的分布式搜索方案,以下场景适合使用SolrCloud

当你需要容错,分布式索引和分布式检索能力时使用SolrCloud。
当索引量很大,搜索请求并发很高时,同样需要使用SolrCloud来满足这些需求

特点

集中式的配置信息
自动容错
近实时搜索
查询时自动负载均衡

2.Solrcloud的结构

Solrcloud结构图

Solr入门_solr_23

物理结构 三个Solr实例( 每个实例包括两个Core),组成一个SolrCloud。

core:
每个Core是Solr中一个独立运行单位,提供 索引和搜索服务

逻辑结构 索引集合包括两个Shard(shard1和shard2),shard1和shard2分别由三个Core组成,其中一个 Leader两个Replication,Leader是由zookeeper选举产生,zookeeper控制每个shard上三个Core的索引数据一致,解决高可用问题。用户发起索引请求分别从shard1和shard2上获取,解决高并发问题。

Master&Slave:
Master是master-slave构中的主结点(通常说主服务器),Slave是master-slave结构中的从结
点(通常说从服务器或备服务器)。
Shard:
一个shard需要由一个Core或多个Core组成。Collection的逻辑分片。每个Shard被化成一个或者多
个replication,通过选举确定哪个是Leader。索引集合包括两个Shard(shard1和shard2),
shard1和shard2分别由三个Core组成,其中一个Leader两个Replication,Leader是由zookeeper选
举产生,zookeeper控制每个shard上三个Core的索引数据一致,解决高可用问题。用户发起索引请求分
别从shard1和shard2上获取,解决高并发问题。
collection:
多个shard组成所以collection一般由多个core组成。
Collection在SolrCloud集群中是一个逻辑意义上的完整的索引结构。它常常被划分为一个或多个
Shard(分片),它们使用相同的配置信息。
比如:针对商品信息搜索可以创建一个collection。
collection=shard1+shard2+....+shardX

3.环境搭建

系统搭建结构图 solrcloud是基于solr和zookeeper部署,zookeeper是一个集群管理软件,solrcloud需要由多台solr服务器组成,然后由zookeeper来进行协调管理。

Solr入门_分词器_24

搭建ZK集群

准备一台centos 7服务器
安装 java -version  
Zookeeper集群安装 第一步:把 zookeeper 的压缩包上传到服务器 解压缩。 第二步:在每个 zookeeper 目录下创建一个 data 目录。 第三步:把 zookeeper 复制三份。  
[root[@localhost](https://my.oschina.net/u/570656) ~]# mkdir /usr/local/solrcloud
[root[@localhost](https://my.oschina.net/u/570656) ~]# cp -r zookeeper-3.4.10
/usr/local/solr-cloud/zookeeper01
[root[@localhost](https://my.oschina.net/u/570656) ~]# cp -r zookeeper-3.4.10
/usr/local/solr-cloud/zookeeper02
[root[@localhost](https://my.oschina.net/u/570656) ~]# cp -r zookeeper-3.4.10
/usr/local/solr-cloud/zookeeper03

在 data 目录下创建一个 myid 文件,文件名就叫做“myid”。内容就是每个实例的id。例如 1、2、3 [root@localhost data]# echo 1 >> myid (或者使用vim) 第五步:修改配置文件。把 conf 目录下的 zoo_sample.cfg 文件改名为 zoo.cfg 注意其它的zookeeper的dataDir和clientPort  
cd /usr/local/solr-cloud/zookeeper01/conf/
> mv zoo_sample.cfg zoo.cfg
> vim zoo.cfg
tickTime=2000
dataDir=/usr/local/solr-cloud/zookeeper01/data
clientPort=2181
initLimit=10
syncLimit=5
server.1=192.168.211.137:2881:3881
server.2=192.168.211.137:2882:3882
server.3=192.168.211.137:2883:3883

启动测试  
# 在三台机器上分别执行
> zkServer.sh start
# 查看状态
[root@solr-1 zookeeper01]# zkServer.sh status
ZooKeeper JMX enabled by default
Using config: /usr/local/solr-cloud/zookeeper01/bin/../conf/zoo.cfg
Mode: follower
[root@solr-2 zookeeper02]# zkServer.sh status
ZooKeeper JMX enabled by default
Using config: /usr/local/solr-cloud/zookeeper02/bin/../conf/zoo.cfg
Mode: leader
[root@solr-3 zookeeper03]# zkServer.sh status
ZooKeeper JMX enabled by default
Using config: /usr/local/solr-cloud/zookeeper03/bin/../conf/zoo.cfg
Mode: follower

搭建Solr集群

第一步: 先构建一个单机版的Solr

1.上传tomcat 和 solr 压缩包 到/usr/local/solr-cloud 下,tomcat中建立solr工程
tar -xvf apache-tomcat-8.5.55.tar.gz
mv apache-tomcat-8.5.55 tomcat
tar -xvf solr-7.7.3.tgz
cp /usr/local/solr-cloud/solr-7.7.3/server/solr-webapp/webapp -rf
/usr/local/solr-cloud/tomcat/webapps/solr
2.拷贝jar包
cd /usr/local/solr-cloud/solr-7.7.3/server/lib
cp ext/* /usr/local/solr-cloud/tomcat/webapps/solr/WEB-INF/lib/
cp metrics-* /usr/local/solr-cloud/tomcat/webapps/solr/WEB-INF/lib/
3.配置solrhome
首先创建solrhome存储Solr索引文件
mkdir -p /usr/local/solr-cloud/solrhome
复制solr-7.7.3/server/solr目录下所有内容到solrhome
cd /usr/local/solr-cloud/solr-7.7.3/server/solr
cp -r * /usr/local/solr-cloud/solrhome/
4.需要修改solr的web.xml文件 把solrhome关联起来 和 去掉安全认证。
<env-entry>
<env-entry-name>solr/home</env-entry-name>
<env-entry-value>/usr/local/solr-cloud/solrhome</env-entry-value>
<env-entry-type>java.lang.String</env-entry-type>
</env-entry>
<!--
<security-constraint>
......
-->
5.启动tomcat测试
./tomcat/bin/startup.sh
systemctl stop firewalld

第二步:创建四个tomcat实例。每个tomcat运行在不同的端口。8180、8280、8380、8480 分别修改tomcat中的端口 vi tomcat01/conf/server.xml 把原来的8005 换成 8105 之前的 8009换成 8109 之前的 8080 换成 8180 其它的tomcat 也类似修改

<Server port="8105" shutdown="SHUTDOWN"> </Server>
<Connector port="8180" protocol="HTTP/1.1" connectionTimeout="20000"
redirectPort="8443" />
<Connector port="8109" protocol="AJP/1.3" redirectPort="8443" />

第三步:建立classes文件夹 拷贝日志配置文件。

mkdir tomcat01/webapps/solr/WEB-INF/classes
cp /usr/local/solr-cloud/solr-7.7.3/server/resources/log* /usr/local/solrcloud/tomcat01/webapps/solr/WEB-INF/classes

其它的tomcat中的操作 参考上面的修改即可

第四步:把单机版solrhome 复制为solrhome1 solrhome2 solrhome3 solrhome4。

cp solrhome -rf solrhome1
cp solrhome -rf solrhome2
cp solrhome -rf solrhome3
cp solrhome -rf solrhome4

第五步:配置solrCloud相关的配置。每个solrhome下都有一个solr.xml,把其中的ip及端口号配置 好。 这里重点是 hostPort 要和tomcat 对应 如果是多台机器 ip 设置不同即可 vi solrhome1/solr.xml 其它的solrhome/solr.xml 依次修改

<solrcloud>
<str name="host">192.168.211.137</str>
<int name="hostPort">8180</int>
<str name="hostContext">${hostContext:solr}</str>
</solrcloud>

第六步:让zookeeper统一管理配置文件。需要把 solrhome/configsets/sample_techproducts_configs/conf目录上传到zookeeper。上传任意 solrhome中的配置文件即可。要保证zookeeper集群是启动状态。 使用工具上传配置文件:solr-7.7.3/server/scripts/cloud-scripts/zkcli.sh

cd /usr/local/solr-cloud/solr-7.7.3/server/scripts/cloud-scripts
./zkcli.sh -zkhost
192.168.211.137:2181,192.168.211.137:2182,192.168.211.137:2183 -cmd upconfig -
confdir /usr/local/solrcloud/solrhome1/configsets/sample_techproducts_configs/conf -confname myconf

第七步:查看zookeeper上的配置文件: 使用zookeeper目录下的bin/zkCli.sh命令查看zookeeper上的配置文件: [root@localhost bin]# ./zkCli.sh [zk: localhost:2181(CONNECTED) 0] ls / [configs, zookeeper] [zk: localhost:2181(CONNECTED) 1] ls /configs [myconf] [zk: localhost:2181(CONNECTED) 2] ls /configs/myconf 第八步:修改tomcat/bin目录下的catalina.sh 文件,关联solr和zookeeper。 把此配置添加到配置文件中: vi中搜索 umask JAVA_OPTS="-DzkHost=192.168.211.137:2181,192.168.211.137:2182,192.168.211.137:2183" 第九步:检查每个tomcat中项目的web.xml 看是否已经对应到对应的solrhome 检查没有问题可以启 动全部tomcat tomcat01 中的web.xml 其它对应的修改 vi tomcat01/webapps/solr/WEB-INF/web.xml

solr/home
/usr/local/solr-cloud/solrhome1
java.lang.String

启动每个tomcat实例。

chmod -R 777 tomcat01/bin
chmod -R 777 tomcat02/bin
chmod -R 777 tomcat03/bin
chmod -R 777 tomcat04/bin

vi tomcat_start.sh

tomcat01/bin/startup.sh
tomcat02/bin/startup.sh
tomcat03/bin/startup.sh
tomcat04/bin/startup.sh

chmod 777 tomcat_start.sh ./tomcat_start.sh 第十步:访问集群

http://192.168.211.137:8180/solr/index.html 查看里面的 cloud 菜单 第十一步:创建新的Collection进行分片处理 点击页面的Collections按钮,然后就能添加了,我这里选择的是名字叫mycollection,用自己上传的 myconf配置文件,有2片shard,每个shard有2个备份节点一主一备

Solr入门_分词器_25

然后回去看下,这样solr集群就搭建ok了!

Solr入门_solr_26