企业级搜索服务器solr

上篇文章我们讲到Lucene,Lucene在创建索引,维护索引时相当繁琐,这些slor都可以解决。

         Solr是一个高性能,采用Java开发,基于Lucene的全文搜索服务器。同时对其进行了扩展,提供了比Lucene更为丰富的查询语言,同时实现了可配置、可扩展并对查询性能进行了优化,并且提供了一个完善的功能管理界面,是一款非常优秀的全文搜索引擎。

Solr可以独立运行,运行在Jetty、Tomcat等这些Servlet容器中,Solr 索引的实现方法很简单,用 POST 方法向 Solr 服务器发送请求添加、删除、更新索引,发送 HTTP GET 请求来查询。

一、solr的目录结构

       

                                                                   example下目录结构

bin:solr的运行脚本

contrib:solr的一些贡献软件/插件,用于增强solr的功能。

dist:该目录包含build过程中产生的war和jar文件,以及相关的依赖文件。

docs:solr的API文档

example:solr工程的例子目录:

l example/solr:

该目录是一个包含了默认配置信息的Solr的Core目录。

l example/multicore:

该目录包含了在Solr的multicore中设置的多个Core目录。

l example/webapps:

    该目录中包括一个solr.war,该war可作为solr的运行实例工程。

licenses:solr相关的一些许可信息

1,重点介绍example下的三个文件夹,搭建slor服务器必须用到的(如上图所示)

lib/ext/下的五个jar包,为slor独有的包

webapps/下的slor.war(直接扔到tomcat下)

slor:称为 家。存放索引的库(数据库)

slor/collection1  下自动生成data/index来存放索引

也可以有collection2 来存放索引

二、搭建单机版slor(分三步)

1,把slor.war放到tomcat的webapps下,解压后得slor文件夹

2,把lib/ext/下的五个jar包 依赖包 放到slor下的lib目录下

3,自己建立个索引库(家)solrhome,将原包下的家内容 复制到该目录下(自己建立家方便后面搭集群)

修改D:\solar\apache-tomcat-7.0.53\webapps\solr\WEB-INF 下的web.xml文件,配置索引库(家)的路径

启动tomcat,访问http://localhost:8080/solr

三、schema.xml配置文件(只有这个文件里有的域才可以用)

1,域

solrhome\collection1\conf目录下有个schema.xml配置文件(该配置文件用来配置域相关信息),在上篇文章中Luncene中是用代码去设置。(是否分析、是否索引、是否保存、是否多值)

2,动态域

域的名称符合就行(如*_i:1_i、qq_i、aa_i都可以)

3,复制域

搜索两个以上域时

比如说当在电商网站搜索:名称(域)+描述(域)时,会将这两个域拷贝到text域中,这样搜索一个text中就行

4,主键id(每个Filed都必须要有的,唯一不可重复)

四、配置中文分词器(分四步)

1,把IKAnalyzer2012FF_u1.jar添加到solr/WEB-INF/lib目录下

2,复制IKAnalyzer的配置文件和自定义词典和停用词词典到solr的classpath下

3,在schema.xml中添加一个自定义的fieldType,使用中文分析器

<!-- IKAnalyzer-->
    <fieldType name="text_ik" class="solr.TextField">
      <analyzer class="org.wltea.analyzer.lucene.IKAnalyzer"/>
    </fieldType>

4,定义field,指定field的type属性为text_ik

<!--IKAnalyzer Field-->
   <field name="title_ik" type="text_ik" indexed="true" stored="true" />
   <field name="content_ik" type="text_ik" indexed="true" stored="false" multiValued="true"/>

五,solr管理台查询页面介绍

q:搜索的关键词

fq:以关键词为结果基础上过滤

sort:排序

start,rows:从第几个开始展示,展示几个

fl:需要搜索哪些Filed(域)

df:默认域(当q中没有设置域,只有域值时,则搜索默认域)

wt:返回数据格式

hl:高亮(关键词显示指定颜色)

六、批量导入数据(分三步)

提前备好数据库数据,每个字段相当于一个Filed,一条数据相当于一个Document

1,把相关jar包和数据库驱动放到D:\solar\solrhome\collection1\lib下

2,配置solrconfig.xml文件,添加一个requestHandler

<requestHandler name="/dataimport"

class="org.apache.solr.handler.dataimport.DataImportHandler">

    <lst name="defaults">

      <str name="config">data-config.xml</str>

     </lst>

  </requestHandler> 

3,创建一个data-config.xml(与solrconfig.xml同级目录)

<?xml version="1.0" encoding="UTF-8" ?>  
<dataConfig>   
<dataSource type="JdbcDataSource"   
		  driver="com.mysql.jdbc.Driver"   
		  url="jdbc:mysql://localhost:3306/lucene"   
		  user="root"   
		  password="root"/>   
<document>   
	<entity name="product" query="SELECT pid,name,catalog_name,price,description,picture FROM products ">
		 <field column="pid" name="id"/> 
		 <field column="name" name="product_name"/> 
		 <field column="catalog_name" name="product_catalog_name"/> 
		 <field column="price" name="product_price"/> 
		 <field column="description" name="product_description"/> 
		 <field column="picture" name="product_picture"/> 
	</entity>   
</document>   

</dataConfig>

4,在schema.xml中添加业务系统Field

<!--product-->
   <field name="product_name" type="text_ik" indexed="true" stored="true"/>
   <field name="product_price"  type="float" indexed="true" stored="true"/>
   <field name="product_description" type="text_ik" indexed="true" stored="false" />
   <field name="product_picture" type="string" indexed="false" stored="true" />
   <field name="product_catalog_name" type="string" indexed="true" stored="true" />

   <field name="product_keywords" type="text_ik" indexed="true" stored="false" multiValued="true"/>
   <copyField source="product_name" dest="product_keywords"/>
   <copyField source="product_description" dest="product_keywords"/>

 重启tomcat

以上完成后我们就在索引库中建立了自己业务系统中的索引

七、使用SolrJ管理索引库

solrj是访问Solr服务的java客户端,提供索引和搜索的请求方法,SolrJ通常在嵌入在业务系统中,通过SolrJ的API接口操作Solr服务

1,导入核心包

2,简单的增删改代码实现

public void addDocument() throws Exception {
        //索引库中添加索引
		//和solr服务器创建连接
		//参数:solr服务器的地址
		SolrServer solrServer = new HttpSolrServer("http://localhost:8080/solr");
		//创建一个文档对象
		SolrInputDocument document = new SolrInputDocument();
		//向文档中添加域
		//第一个参数:域的名称,域的名称必须是在schema.xml中定义的
		//第二个参数:域的值
		document.addField("id", "c0001");
		document.addField("title_ik", "使用solrJ添加的文档");
		document.addField("content_ik", "文档的内容");
		document.addField("product_name", "商品名称");
		//把document对象添加到索引库中
		solrServer.add(document);
		//提交修改
		solrServer.commit();

        //根据id删除文档
		solrServer.deleteById("c0001");
		//提交修改
		solrServer.commit();

        //solrJ中只有add方法没有update,只要添加一条新的文档和被修改的id一样即可

3,复杂查询代码演示(重点)  其中包含查询、过滤、分页、排序、高亮显示等处理

@Test
	public void queryIndex2() throws Exception {
        //其中包含查询(关键词)、过滤、分页、排序、高亮显示等处理
		//创建连接
		SolrServer solrServer = new HttpSolrServer("http://localhost:8080/solr");
		//创建一个query对象
		SolrQuery query = new SolrQuery();
		//设置查询条件
		query.setQuery("钻石");
		//过滤条件
		query.setFilterQueries("product_catalog_name:幽默杂货");
		//排序条件
		query.setSort("product_price", ORDER.asc);
		//分页处理
		query.setStart(0);
		query.setRows(10);
		//结果中域的列表
		query.setFields("id","product_name","product_price","product_catalog_name","product_picture");
		//设置默认搜索域
		query.set("df", "product_keywords");
		//高亮显示
		query.setHighlight(true);
		//高亮显示的域
		query.addHighlightField("product_name");
		//高亮显示的前缀
		query.setHighlightSimplePre("<em>");
		//高亮显示的后缀
		query.setHighlightSimplePost("</em>");
		//执行查询
		QueryResponse queryResponse = solrServer.query(query);
		//取查询结果
		SolrDocumentList solrDocumentList = queryResponse.getResults();
		//共查询到商品数量
		System.out.println("共查询到商品数量:" + solrDocumentList.getNumFound());
		//遍历查询的结果
		for (SolrDocument solrDocument : solrDocumentList) {
			System.out.println(solrDocument.get("id"));
			//取高亮显示,高亮的结果在另外一个容器Map中
			String productName = "";
			Map<String, Map<String, List<String>>> highlighting = queryResponse.getHighlighting();
			List<String> list = highlighting.get(solrDocument.get("id")).get("product_name");
			//判断是否有高亮内容
			if (null != list) {
				productName = list.get(0);
			} else {
				productName = (String) solrDocument.get("product_name");
			}
			
			System.out.println(productName);
			System.out.println(solrDocument.get("product_price"));
			System.out.println(solrDocument.get("product_catalog_name"));
			System.out.println(solrDocument.get("product_picture"));

八、solr在企业中的应用(以京东为例搜索)

 

思路:前端提交一个form表单参数,form表单中包含很多个域(关键词、还有隐藏域(品牌、分类、操作系统、屏幕尺寸、高级选项等)),

比如搜索“手机”(默认域)关键词。每次点击搜索时,把关键词(默认域)传给后台进行搜索(其他隐藏域进行清空(value="")),后面再选品牌、 操作系统、屏幕尺寸等域和关键词域进行过滤一起传给后台实施查询,代码跟上诉复杂查询一样。

九、solr集群之SolrCloud

黄色线上三个节点索引库数据是一样的,蓝色线上三个也是一样,组合成一个整个索引库

集群特点:高并发(负载均衡)、高可用(主从节点,主节点挂了,从节点工作)、海量存储(扩容)

solr集群依赖zookeeper(为防止zookeeper挂了整个solr集群挂了),所以zookeeper也要搭建集群(奇数点,投票机制)

 

集群的搭建就不在这讲了。

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值