zoukankan      html  css  js  c++  java
  • Apache Solr采用Java开发、基于Lucene的全文搜索服务器

    http://docs.spring.io/spring-data/solr/

    首先介绍一下solr:

    Apache Solr (读音: SOLer) 是一个开源、高性能、采用Java开发、基于Lucene的全文搜索服务器,文档通过Http利用XML加到一个搜索集合中,查询该集合也是通过 http收到一个XML/JSON响应来实现。Solr 中存储的资源是以 Document 为对象进行存储的。每个文档由一系列的 Field 构成,每个 Field 表示资源的一个属性。Solr 中的每个 Document 需要有能唯一标识其自身的属性,默认情况下这个属性的名字是 id,在 Schema 配置文件(schema.xml)中使用:<uniqueKey>id</uniqueKey>进行描述。solr有两个核心文件,solrconfig.xml和schema.xml。solrconfig.xml是solr的基础文件,里面配置了各种web请求处理器、请求响应处理器、日志、缓存等;schema.xml配置映射了各种数据类型的索引方案,分词器的配置、索引文档中包含的字段也在此配置。

    工作中主要用来分词和搜索,简单的工作原理是:利用分词器对数据源进行分词处理,然后根据分词结果建立索引库;查询的时候,利用分词器对查询语句进行分词,根据查询语句分词的结果在索引库中进行匹配,最后返回结果。

    废话少说,下面开始solr之旅吧:

    一.安装JDK和Tomcat

    (1):安装jdk  下载jdk安装包,解压到jdk-1.x目录

    (2):安装tomcat,下载tomcat安装包,解压到apache-tomcat目录下

    修改tomcat安装目录下的conf目录的server.xml

    找到<Connector port="8080" .../>,加入URIEncoding="UTF-8",为了支持中文。

    设置Java和tomcat环境变量

    上面两步比较简单,这里就只简单描述一下,不明白的可以网上查资料。

    二. 安装solr

    下载solr包,http://labs.renren.com/apache-mirror/lucene/solr/3.5.0/apache-solr-3.5.0.zip

    解压缩到apache-solr目录,把apache-solr/dist目录下的apache-solr-3.5.0.war 复制到$TOMCAT_HOME/webapps目录下,重命名为solr.war

    复制apache-solr/example/solr到tomcat根目录下(如果你想配置多core(实例),就复制apache-solr/example/multicore到tomcat根目录下,不用复制solr了),作为solr/home,以后也可以往该目录添加 core,每个core下面都可以有自己的配置文件。

    在apache-tomcat/conf/Catalina/localhost/下创建solr.xml(跟webapps下的solr项目同名),指定solr.war和solr/home的位置,让tomcat启动时就自动加载该应用。

    solr.xml内容如下:

    <?xml version="1.0" encoding="UTF-8"?>

    <Context docBase="/home/zhoujh/java/apache-tomcat7/webapps/solr.war" debug="0" crossContext="true" >

       <Environment name="solr/home" type="java.lang.String" value="/home/zhoujh/java/apache-tomcat7/solr" override="true" />

    </Context>

    然后在tomcat的bin目录下执行./startup.sh,启动tomcat

    在地址栏访问http://localhost:8080/solr/

    将会出现solr欢迎界面和admin入口

    注:如果出现org.apache.solr.common.SolrException: Error loading class 'solr.VelocityResponseWriter' 异常,最简单的解决方法:找到$TOMCAT_HOME/solr/conf/solrconfig.xml,把<queryResponseWriter name="velocity" class="solr.VelocityResponseWriter" enable="${solr.velocity.enabled:true}"/>注释掉或者enable:false即可。如果一切顺利的话,现在可以看到solr的web管理界面了。不过要想实现分词的功能,得安装一个中文分词器,这里推荐IKAnalyzer或mmseg4j。

    IKAnalyzer是一个开源的,基于java语言开发的轻量级的中文分词工具包,采用了特有的“正向迭代最细粒度切分算法“,具有60万字/秒的高速处理能力,采用了多子处理器分析模式,支持:英文字母(IP地址、Email、URL)、数字(日期,常用中文数量词,罗马数字,科学计数法),中文词汇(姓名、地名处理)等分词处理。优化的词典存储,更小的内存占用。支持用户词典扩展定。

    mmseg4j 用 Chih-Hao Tsai 的 MMSeg 算法(http://technology.chtsai.org/mmseg/ )实现的中文分词器,并实现 lucene 的 analyzer 和 solr 的TokenizerFactory 以方便在Lucene和Solr中使用。MMSeg 算法有两种分词方法:Simple和Complex,都是基于正向最大匹配。Complex 加了四个规则过虑。官方说:词语的正确识别率达到了 98.41%。mmseg4j 已经实现了这两种分词算法。

    三. 配置中文分词器

    下面分别安装这两个中文分词器,当然选择安装其中一个也是可以的。

    (1)安装IKAnalyzer

    下载地址: http://code.google.com/p/ik-analyzer/downloads/list

    在当前目录下新建IKAnalyzer目录,解压到该目录下:unzip IKAnalyzer2012_u5.zip -d ./IKAnalyzer

    把IKAnalyzer目录下的IKAnalyzer2012.jar文件拷贝到 $TOMCAT_HOME/webapps/solr/WEB-INF/lib/下

    配置schema.xml,编辑$TOMCAT_HOME/solr/conf/schema.xml,在文件中添加下面这个fieldtype

    注:下面的代码中多了很多“<span style="font-size: x-small;">”标签,这个是设置字体时iteye编辑器自己生成的。

    Xml代码  收藏代码
    1. <span style="font-size: x-small;"><span style="font-size: x-small;"><span style="font-size: small;"><fieldType name="text" class="solr.TextField" positionIncrementGap="100">  
    2.         <analyzer type="index">  
    3.             <tokenizer class = "org.wltea.analyzer.solr.IKTokenizerFactory" isMaxWordLength="false" />   
    4.             <filter class="solr.StopFilterFactory" ignoreCase="true" words="stopwords.txt" enablePositionIncrements="true" />    
    5.             <filter class="solr.WordDelimiterFilterFactory" generateWordParts="1" generateNumberParts="1" catenateWords="1" catenateNumbers="1" catenateAll="0" splitOnCaseChange="1" />                  
    6.             <filter class="solr.LowerCaseFilterFactory" />    
    7.             <filter class="solr.EnglishPorterFilterFactory" protected="protwords.txt" />        
    8.             <filter class="solr.RemoveDuplicatesTokenFilterFactory" />    
    9.         </analyzer>  
    10.         <analyzer type="query">  
    11.             <tokenizer class = "org.wltea.analyzer.solr.IKTokenizerFactory" isMaxWordLength="true" />    
    12.             <filter class="solr.SynonymFilterFactory" synonyms="synonyms.txt" ignoreCase="true" expand="true" />    
    13.             <filter class="solr.StopFilterFactory" ignoreCase="true" words="stopwords.txt" />    
    14.             <filter class="solr.WordDelimiterFilterFactory" generateWordParts="1" generateNumberParts="1" catenateWords="0" catenateNumbers="0" catenateAll="0" splitOnCaseChange="1" />    
    15.             <filter class="solr.LowerCaseFilterFactory" />    
    16.             <filter class="solr.EnglishPorterFilterFactory" protected="protwords.txt" />    
    17.             <filter class="solr.RemoveDuplicatesTokenFilterFactory" />    
    18.         </analyzer>  
    19.     </fieldType></span></span></span>  

     添加一个索引字段field,并应用上面配置的fieldtype

    Java代码  收藏代码
    1. <span style="font-size: x-small;"><span style="font-size: x-small;"><span style="font-size: small;"><field name="game_name" type="text" indexed="true" stored="true" required="true" />  </span></span></span>  

    然后找到这一句:<defaultSearchField>text</defaultSearchField>把它改成<defaultSearchField>game_name</defaultSearchField>

    在浏览器打开http://localhost:8080/solr/admin/analysis.jsp,就可以进行分词处理了。

    IKAnalyzer添加自定义分词词典:词典文件格式为无BOM的UTF-8编码的文本文件,文件扩展名不限,一次可以添加多个词库,每个词库以";"分开。把IKAnalyzer目录下的IKAnalyzer.cfg.xml和stopword.dic拷贝到$TOMCAT_HOME/webapps/solr/WEB_INF/classes目录下,可以自己新建一个mydic.dic文件,然后在IKAnalyzer.cfg.xml里进行配置。

    (2)安装mmseg4j

     下载地址:http://code.google.com/p/mmseg4j/downloads/list

    在当前目录下新建mmseg4j目录,解压到该目录下:unzip mmseg4j-1.8.5.zip -d ./mmseg4j

    把mmseg4j目录下的mmseg4j-all-1.8.5.jar文件拷贝到 $TOMCAT_HOME/webapps/solr/WEB-INF/lib/下

    配置schema.xml,编辑$TOMCAT_HOME/solr/conf/schema.xml,在文件中添加下面这个fieldtype

    Xml代码  收藏代码
    1. <span style="font-size: x-small;"><span style="font-size: x-small;"><span style="font-size: small;"><fieldtype name="textComplex" class="solr.TextField" positionIncrementGap="100">  
    2.         <analyzer>  
    3.             <tokenizer class="com.chenlb.mmseg4j.solr.MMSegTokenizerFactory" mode="complex" dicPath="/home/zhoujh/java/apache-tomcat7/solr/dict">  
    4.             </tokenizer>  
    5.         </analyzer>  
    6.     </fieldtype>  
    7.     <fieldtype name="textMaxWord" class="solr.TextField" positionIncrementGap="100">  
    8.         <analyzer>  
    9.             <tokenizer class="com.chenlb.mmseg4j.solr.MMSegTokenizerFactory" mode="max-word" dicPath="/home/zhoujh/java/apache-tomcat7/solr/dict">  
    10.             </tokenizer>  
    11.         </analyzer>  
    12.     </fieldtype>  
    13.     <fieldtype name="textSimple" class="solr.TextField" positionIncrementGap="100">  
    14.         <analyzer>  
    15.             <tokenizer class="com.chenlb.mmseg4j.solr.MMSegTokenizerFactory" mode="simple" dicPath="/home/zhoujh/java/apache-tomcat7/solr/dict">  
    16.             </tokenizer>  
    17.         </analyzer>  
    18.     </fieldtype></span></span></span>  

     注意:dicPath的值改成你自己机器上相应的目录。

    然后修改之前添加的filed,让其使用mmseg4j分词器

    Xml代码  收藏代码
    1. <span style="font-size: x-small;"><span style="font-size: x-small;"><span style="font-size: small;"><field name="game_name" type="textComplex" indexed="true" stored="true" required="true" />  </span></span></span>  

     配置mmseg4j分词词典:MMSEG4J的词库是可以动态加载的,词库的编码必须是UTF-8,mmseg4j 默认从当前目录下的 data 目录读取上面的文件,当然也可以指定别的目录,比如我就放在自定义的dict目录下。自定义词库文件名必需是 "words" 为前缀和 ".dic" 为后缀。如:/data/words-my.dic。

    这里直接把mmseg4j/data目录下的所有.dic文件拷贝到$TOMCAT_HOME/solr/dict目录下。共有:4个dic文件,chars.dic、units.dic、 words.dic、 words-my.dic。下面简单解释一下这几个文件的作用。

    1、chars.dic,是单个字,和对应的频率,一行一对,字在全面,频率在后面,中间用空格分开。这个文件的信息是 complex 模式要用到的。在最后一条过虑规则中使用了频率信息。

    2、units.dic,是单位的字,如:分、秒、年。

    3、words.dic,是核心的词库文件,一行一条,不需要其它任何数据(如词长)。

    4、words-my.dic,是自定义词库文件

    在浏览器打开http://localhost:8080/solr/admin/analysis.jsp,就可以看到分词效果了。

    现在,这两种分词方法都已配置好了,想用哪种就把查询的filed的type设置成哪种。

    四. 导入文档数据

    现在添加文本搜索的功能,首先导入数据源。

    切换到/home/zhoujh/java/solr/apache-solr/example/exampledocs目录下,该目录下有很多xml文件,随便copy一个,改名位game_data.xml。如:cp hd.xml game_data.xml,修改内容如下:

    Xml代码  收藏代码
    1. <span style="font-size: x-small;"><span style="font-size: x-small;"><span style="font-size: small;"><add>  
    2. <doc>  
    3.   <field name="id">1</field>  
    4.   <field name="game_name">魔兽世界</field>  
    5. </doc>  
    6. <doc>  
    7.   <field name="id">2</field>  
    8.   <field name="game_name">仙剑</field>  
    9. </doc>  
    10. <doc>  
    11.   <field name="id">3</field>  
    12.   <field name="game_name">传奇</field>  
    13. </doc>  
    14. <doc>  
    15.   <field name="id">4</field>  
    16.   <field name="game_name">极品飞车</field>  
    17. </doc>  
    18. <doc>  
    19.   <field name="id">5</field>  
    20.   <field name="game_name">轩辕剑</field>  
    21. </doc>  
    22. </add></span></span></span>  

    注意:该xml文件必须是UTF-8格式的。

    然后提交到solr,在 /home/zhoujh/java/solr/apache-solr/example/exampledocs目录下执行命令:

    [zhoujh@alexzhou exampledocs]$ java -Durl=http://localhost:8080/solr/update -Dcommit=yes -jar post.jar game_data.xml

    如果输出下面的信息,则导入成功。注:xml文件中要有game_name这个field。如果出错,到$TOMCAT_HOME/logs/下看catalinaxxx.log日志信息

    SimplePostTool: version 1.4

    SimplePostTool: POSTing files to http://localhost:8080/solr/update..

    SimplePostTool: POSTing file game_data.xml

    SimplePostTool: COMMITting Solr index changes..

    检测是否有数据:http://localhost:8080/solr/select/?q=*:*,如果输出信息如下,就成功了。

    Xml代码  收藏代码
    1. <span style="font-size: x-small;"><span style="font-size: small;"><response>  
    2. <lst name="responseHeader">  
    3. <int name="status">0</int>  
    4. <int name="QTime">0</int>  
    5. <lst name="params">  
    6. <str name="indent">on</str>  
    7. <str name="start">0</str>  
    8. <str name="q">*:*</str>  
    9. <str name="rows">10</str>  
    10. <str name="version">2.2</str>  
    11. </lst>  
    12. </lst>  
    13. <result name="response" numFound="5" start="0">  
    14. <doc>  
    15. <str name="game_name">魔兽世界</str>  
    16. <str name="id">1</str>  
    17. </doc>  
    18. <doc>  
    19. <str name="game_name">仙剑</str>  
    20. <str name="id">2</str>  
    21. </doc>  
    22. <doc>  
    23. <str name="game_name">传奇</str>  
    24. <str name="id">3</str>  
    25. </doc>  
    26. <doc>  
    27. <str name="game_name">极品飞车</str>  
    28. <str name="id">4</str>  
    29. </doc>  
    30. <doc>  
    31. <str name="game_name">轩辕剑</str>  
    32. <str name="id">5</str>  
    33. </doc>  
    34. </result>  
    35. </response></span></span>  
      

    不过在现实工作中,一般利用数据库作为数据源,下面我们来配置solr连接数据库源。

     

    五. solr从数据库导入数据

    (1)安装mysql,

    安装完后执行以下命令:启动mysql服务,进入mysql,创建数据库kw_game,创建表game,导入数据

    Sql代码  收藏代码
    1. <span style="font-size: x-small;"><span style="font-size: small;">sudo /etc/init.d/mysqld start  
    2. mysql -u root -p  
    3. create database kw_game;  
    4. use kw_game;  
    5. create table game(id int primary key auto_increment,game_name varchar(100),add_time datetime);  
    6. insert into game(game_name,add_time) values("魔兽世界",now());  
    7. insert into game(game_name,add_time) values("魔兽争霸",now());  
    8. insert into game(game_name,add_time) values("传奇世界",now());</span></span>  

    (2)下载 mysql-connector-java-xx-bin.jar(驱动程序)

    把 mysql-connector-java-5.1.20-bin.jar复制到~/java/apache-tomcat7/webapps/solr/WEB-INF/lib/目录下

    cp mysql-connector-java-5.1.20-bin.jar ~/java/apache-tomcat7/webapps/solr/WEB-INF/lib/

    (2)配置solrconfig.xml,添加一个requestHandler

    Xml代码  收藏代码
    1. <span style="font-size: x-small;"><span style="font-size: x-small;"><span style="font-size: small;"><requestHandler name="/dataimport" class="org.apache.solr.handler.dataimport.DataImportHandler">  
    2.       <lst name="defaults">  
    3.           <str name="config">game-data-config.xml</str>  
    4.       </lst>  
    5.   </requestHandler></span></span></span>  

    (3)新建一个数据源配置文件game-data-config.xml,内容如下

    Java代码  收藏代码
    1. <span style="font-size: x-small;"><span style="font-size: x-small;"><span style="font-size: small;"><?xml version="1.0" encoding="UTF-8"?>  
    2. <dataConfig>  
    3.     <dataSource type="JdbcDataSource"  
    4.         driver="com.mysql.jdbc.Driver"  
    5.         url="jdbc:mysql://localhost:3306/game_db"  
    6.         user="root"  
    7.         password="123456"/>  
    8.   
    9.     <document name="doc">  
    10.         <entity name="game" query="select * from game"   
    11.             deltaImportQuery="select * from game where id='${dataimporter.delta.id}'"  
    12.             deltaQuery="select id from game where add_time > '${dataimporter.last_index_time}'">  
    13.             <field column="id" name="id" />  
    14.             <field column="game_name" name="game_name" /><field column="add_time" name="add_time" />  
    15.         </entity>  
    16.     </document>  
    17. </dataConfig></span></span></span>  

     注: deltaImportQuery、deltaQuery:增量更新时用到,因为在schema.xml中已经有game_name和id字段了,只需在schmema.xml添加add_time字段,格式为date或者string。

    在浏览器输入下面两个地址,导入数据创建索引。

    更新全部: http://localhost:8080/solr/dataimport?command=full-import

    增量更新: http://localhost:8080/solr/dataimport?command=delta-import

    然后检测是否有数据:http://localhost:8080/solr/select/?q=*:*,现在页面上出现的就是你数据库里的数据了。

    注:如果出现了下面异常:

    Error loading class 'org.apache.solr.handler.dataimport.DataImportHandler

    是solrconfig.xml文件中<lib dir="xx/dist/  regex="" /> dir的路径错了,改成你电脑上正确的位置就ok了~~

    六. 配置多个实例

    最后简单介绍一下如何配置多个实例,编辑$TOMCAT_HOME/solr/solr.xml

    Xml代码  收藏代码
    1. <span style="font-size: x-small;"><span style="font-size: small;"><cores adminPath="/admin/cores">  
    2.     <core name="game" instanceDir="game" /> <core name="game2" instanceDir="game2" />  
    3.    
    4.   </cores></span></span>  

    此时访问的时候必须得在solr后加上各实例的名称

    http://localhost:8080/solr/game/admin

    http://localhost:8080/solr/game2/admin

  • 相关阅读:
    第04组 Alpha冲刺(1/6)
    第04组 团队Git现场编程实战
    第04组 团队项目-需求分析报告
    Codeforces 652F 解题报告
    团队项目-选题报告
    php 基础 字符串转整形
    php 基础 判断类型
    php 基础 自动类型转换
    php 算false的情况
    php redis 集群扩展类文件
  • 原文地址:https://www.cnblogs.com/fx2008/p/4170978.html
Copyright © 2011-2022 走看看