Solr的使用说明文档

Swear_Max 贡献于2013-01-15

作者 zhuchangxin  创建于2012-08-13 03:17:00   修改者liupeng  修改于2012-09-21 06:02:00字数12400

文档摘要:Solr 是一种开放源码的、基于 Lucene Java 的搜索服务器,易于加入到 Web 应用程序中。Solr 提供了层面搜索、命中醒目显示并且支持多种输出格式(包括 XML/XSLT 和 JSON 格式)。它易于安装和配置,而且附带了一个基于 HTTP 的管理界面。您可以坚持使用 Solr 的表现优异的基本搜索功能,也可以对它进行扩展从而满足企业的需要。Solr 还拥有一个活跃的开发者群体,如有需要,您可以随时向他们寻求帮助。
关键词:

 Tomcat7,solr3.6,mmseg1.8 1:环境的搭建 1:解压tomcat,solr,mmseg4j 2:复制dist文件夹下apache-solr.war到tomcat的webapp文件夹下,修改文件名为solr(不该也行,这里修改文件名方便一会地址栏的输入) 3:创建solr-tomcat文件夹作为solr的根目录 4:tomcat/conf/Catalina/localhost文件夹(不存在手动创建)下创建solr.xml,文件内容如下,根据情况,修改相应的路径 此步骤可以不执行,而是在 solr.war 解压后,将web.xml的此处做修改,指向合适的位置。 5:复制solr解压后,example文件夹下的solr文件夹到solr-tomcat文件夹下 6:访问http://localhost:8080/solr/,验证是否配置成功(访问后,solr-tomcat/solr文件夹下会多一个data文件夹) 2:配置文件的说明 1:apache-tomcat-7.0.19\conf\Catalina\localhost\solr.xml文件,用来配置solr的根目录,目前只用到一次 2:E:\solr-tomcat\solr\solr.xml文件,目前只看到在配置多核时用到,后面讲 3:E:\solr-tomcat\solr\conf\schema.xml文件(非常重要) 配置域的类型 配置域,在doc文档中的用到的field和solrj中用到的域名必须在这里配置。Index表示是否需要索引,stored是否需要存储,multiValued表示是否有多个值 就是动态匹配 在搜索时可以直接通过“zhang san”来搜索,不需要在通过“name:zhang san”来搜索 4:E:\solr-tomcat\solr\conf\solrconfig.xml文件:缓存,请求的配置,索引的配置 3:浏览器客户端的说明 Solr->analyze:分词 Query String:根据索引搜索时用。eg:name:zhang san可以通过name来搜索姓名是zhang san的人。如果配置了copyField也可以直接通过zhang san来搜索 4:中文分词的配置 1:解压mmseg4j,拷贝mmseg4j-all-1.8.5.jar到tomcat\webapp\solr的lib目录下 2:solr-tomcat\solr下创建dic文件夹,存放词库;拷贝mmseg4j下的words.dic到该目录下 3:修改schema.xml文件,添加如下代码(注意修改路径) 4:测试中文分词是否起作用 复制一段中文到Field value中;Field选择name输入complex,测试分词 name在使用name(没有配置中文分词,使用默认的)再次进行测试 5:多核的配置 1:拷贝example\multicore文件夹下的core0,core1,solr.xml到solr-tomcat\solr文件夹下 2:方位http://localhost:8080/solr/ 使用浏览器客户端创建索引,搜索 4:创建索引(xml,json,cvs格式的文件cookbook),确保文件夹下面有post.jar文件 1:复制solr解压后的,example文件夹下的exampledocs目录到solr-tomcat下(里面包含了一些测试索引用到的文件) 2:命令行创建索引:E:\solr-tomcat\exampledocs>java -Durl=http://localhost:8080/solr/update -Dcommit=yes -jar post.jar m*.xml,对该文件夹下所有以m开头的xml文件创建索引,此时solr-tomcat\solr\data文件夹下多了一些文件,有段文件,域文件,索引文件等 3:通过浏览器进行搜索,必须通过一个完整的分词(一个完整的单词,不能用a,m,z等搜索,同时this,that等也不能用于搜索) 5:更新索引 更新索引一般都是通过删除索引,然后再创建 6:删除索引 Solrj的使用 http://wiki.apache.org/solr/Solrj private static final String DEFAULT_URL = "http://localhost:8080/solr/"; 1:创建索引(如何对一个指定格式的xml创建索引还不清楚) 对文件进行索引 public void index() throws SolrServerException, IOException { SolrServer solrServer = new HttpSolrServer(DEFAULT_URL); SolrInputDocument document = new SolrInputDocument(); document.addField("id", "1"); //id必须有 document.addField("name", "test"); document.addField("path", "测试"); //path需要在schema.xml中定义 solrServer.add(document); solrServer.commit(); } 对Bean进行索引 数据库中的数据: Student实体类: import org.apache.solr.client.solrj.beans.Field; public class Student implements Serializable { private static final long serialVersionUID = 1L; @Field private Long id; @Field private String name; @Field private Date birthday; @Field private String email; private Integer age; private String introduction; ... } Action方法 public String createBeanIndex() { solrService.createBeanIndex(); return SUCCESS; } Service方法 private SolrServer solrServer = null; private static final String DEFAULT_URL = "http://localhost:8080/solr/"; public void init() { // CommonsHttpSolrServer solrServer = new HttpSolrServer(DEFAULT_URL); } public void createBeanIndex() { solrIndex.addBeans(dao); } SolrIndex方法 public void addBeans(CommonDao dao) { try { dao.createIndex(solrServer); solrServer.commit(); } catch (SolrServerException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } Dao的方法 public void createIndex(SolrServer server) { Session session = sf.openSession(); DetachedCriteria d = DetachedCriteria.forClass(Student.class); Criteria criteria = d.getExecutableCriteria(session); criteria.setProjection(null); criteria.setResultTransformer(CriteriaSpecification.ROOT_ENTITY); ScrollableResults sr=criteria.scroll(ScrollMode.FORWARD_ONLY); while(sr.next()) { try { server.addBean(sr.get()[0]); } catch (HibernateException e) { e.printStackTrace(); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (SolrServerException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } 搜索 Action public String queryBeans() { list = solrService.queryBean(keyWord); return SUCCESS; } Service public List queryBean(String keyWord) { return solrIndex.query("name:" + keyWord); // return solrIndex.query("*:*"); // return solrIndex.queryAll(); } SolrIndex public SolrDocumentList query(String str) { SolrQuery query = new SolrQuery(str); QueryResponse response = new QueryResponse(); SolrDocumentList list = null; try { response = solrServer.query(query); list = response.getResults(); return list; } catch (SolrServerException e) { e.printStackTrace(); } return null; } 搜索zhang时,返回结果 Name:zhang返回的结果 *:*返回的结果 删除索引 Action public String deleteIndex() { solrService.deleteIndex(); return SUCCESS; } Service public void deleteIndex() { solrIndex.delete("*:*"); } SolrIndex public void delete(String params) { try { solrServer.deleteByQuery(params); solrServer.commit(); } catch (SolrServerException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } 删除索引后再次搜索,结果为空 高亮显示 solrIndex类 public SolrDocumentList query(String str) { SolrQuery query = new SolrQuery(str); //设置高亮,以下两种方式都行(相当于开启高亮功能) //query.setHighlight(true); query.setParam("hl", "true"); //highlighting //设置高亮显示的请求,高亮显示的内容由该参数决定,但是返回结果还是由SolrQuery决定 //query.setParam("hl.q", "email:zhang@ppstream.com"); query.setParam("hl.fl", "name"); //高亮显示字段前后添加html代码 query.setHighlightSimplePre(""); query.setHighlightSimplePost(""); SolrDocumentList list = new SolrDocumentList(); SolrDocument document = null; QueryResponse response = new QueryResponse(); try { response = solrServer.query(query); } catch (SolrServerException e1) { e1.printStackTrace(); } try { SolrDocumentList documents = response.getResults(); //第一个Map的键是文档的ID,第二个Map的键是高亮显示的字段名 Map>> map = response.getHighlighting(); for(int i=0;i1000实现(默认是1万)。这里是分词数量,不是汉字或字母的个数。 2:配置中文分词后,如果查询“java编程思想”,会自动拆分成java,编程,思想3个分词依次进行查找 Mmseg4j有max-word,complex,simple三种分词模式,max-word分词力度最细(eg:“数据库”会被拆分成“数据”“库”两个词),另外两种模式会将“数据库”当做一个分词 3:多条件查询 可以通过“编程 AND empName:XXX”进行查询,或者“编程 OR empName:XXX”等 4:字段当做一个整体,不进行分词 如果某个字段不需要使用分词,eg:java编程思想,只有在输入完成的书名:java编程思想才会搜索出来,可以在书名字段上的type使用不带分词的类型(schema.xml中配置) 5:检索索引中的部分字段 有时索引中可能存放很多信息,eg:书名,作者,出版时间,ISBN…….;在某次查询中,我们只需要搜索结果书名和作者即可。可以通过如下方式实现 SolrQuery query = new SolrQuery(param); //返回的结果 String[] str = {"title", "author"}; query.setFields(str); 6:Solr的分页 SolrQuery query = new SolrQuery("*:* AND (empName:XXX OR empName:XX)"); query.setHighlight(true); query.setStart(0); query.setRows(2); QueryResponse response = solrServer.query(query); long totalCount = response.getResults().getNumFound(); totalCount返回的是满足条件的总记录条数,并不一定是0或2 7:solrj高亮显示时,只显示字段部分内容 SolrDocumentList list = response.getResults(); Map>> map = response.getHighlighting(); //对应的高亮字段(假设是content)。在list中显示正确,map中显示的只是content中的一部分。 query.setHighlightFragsize(100000); //可以通过这种方法改变,设置一个比list中,对应content内容大的数字 query.setHighlightSnippets(0);//或者设置高亮片段为0,这样关键字也就不会在高亮显示 8:搜索条件的部分关键字高亮显示 有时我们查询根据条件“java OR (empId:1000 AND empId:1001)”搜索时,结果如果高亮显示,可能出现1000,1001数字也会高亮,但是我们只希望java关键字高亮,这个时候可以用下面的方法 query.setParam("hl.q", "lucene solr");只对lucene和solr关键字进行高亮显示(solr不作为搜索条件也可以) 9:显示第一个匹配关键字附近的部分内容 有时我们需要显示检索出内容的一部分(在列表页,只需要显示一个概要信息),这时候可以通过设置query.setHighlightFragsize(100000);的大小来控制 10:schema文件,copyField配置 11:自动补全 搜索时在title和content上进行搜索,所以自动补全时要在title和content上同时进行。但是自动补全只能在一个字段上进行(目前我知道这样),所以就创建一个新字段searchField=title+”,”+content用来进行自动补全的提示,该字段仅用来索引不需要存储。 SolrQuery query = new SolrQuery(q); query.addTermsField(searchField); query.setTerms(true); query.setTermsLimit(limit); query.setTermsLower(pre); query.setTermsPrefix(pre); query.setQueryType("/terms"); QueryResponse qr = solrServer.query(query); TermsResponse resp = qr.getTermsResponse(); List list = resp.getTerms(searchField); 这种搜索存在的问题: 1: q:empName:XXX AND projecteId:19 pre:lucen 在搜索时,返回的TermsResponse结果只应用了pre一个条件 2: title,content无法配置copyField字段使用complex(原因及解决办法没找到) 解决方法:改用Facet替换Term SolrQuery query = new SolrQuery(q); query.setFacet(true); query.addFacetField(searchField); query.setFacetLimit(limit); query.setFacetPrefix(pre); QueryResponse qr = solrServer.query(query); List fss = qr.getFacetFields(); FacetField ff = fss.get(0); return ff.getValues(); 返回的fss结果仍然是根据pre一个条件返回的结果集,但是不满足条件query的结果集中,对应的count为0,即出现了0次 12:solr删除索引后,索引文件还存在,但是搜索结果已经不存在 在lucene中删除索引,是通过将索引文件标记为rm,在此检索的时候,标记为rm的索引将检索不出来,但是查询索引文档总数时,还是会计算在内。当需要删除的文档达到一定数量之后才会批量删除,solr中不知道是不是因为这个原因 13:添加tomcat验证,防止用户直接通过地址栏访问solr,进行修改删除索引 1:修改tomcat-user.xml文件 2:修改solr的web.xml文件,添加如下代码,对所有的请求,都需要tomcat用户及密码的验证 solr /* GET POST This applies only to the "tomcat" security role admin BASIC admin 3:使用该方法后,通过solrj也不能直接访问,修改如下 String url = PropertiesSon.getText("solr.serverUrl"); String username = PropertiesSon.getText("solr.username"); String password = PropertiesSon.getText("solr.password"); String host = PropertiesSon.getText("solr.host"); int port = Integer.parseInt(PropertiesSon.getText("solr.port")); DefaultHttpClient httpclient = new DefaultHttpClient(); httpclient.getCredentialsProvider().setCredentials( new AuthScope(host, port), new UsernamePasswordCredentials(username, password)); solrServer = new HttpSolrServer(url, httpclient); 4:使用该方法创建时,删除添加索引报错“Cannot retry request with a non-repeatable request entity.” 修改方法:url用http://username:password@10.1.11.165:8081/solr取代http://10.1.20.57:8081/solr(httpclient使用 4.2是时正常,使用4.1时,在删除新增索引仍然会报上面的错误) 14:tomcat编码问题 待实现: 1. 一个下拉框,给出分类选择 2. 用户输入关键字查询,但关键字是错误的,给出正确的提示 3. 大家还搜索过提示 4. 根据拼音,给出相应的汉语关键词提示 5. 选择后,还有第二次的全文检索,如果能检索出内容,给出右箭头,如果不能检索出相应结果,没有右箭头 6. 分布式检索 SolrCloud 相关知识: 1. Multicore 将core查询分发给core_0 和core_1? 以及合并core_0和core_1的结果给core solrconfig.xml 中加上shards相关的参数 http://www.cnblogs.com/huangfox/archive/2012/02/10/2345335.html http://blog.chenlb.com/2009/01/solr-multicore-work-with-solr-distributed-searching-to-search-big-index.html http://blog.csdn.net/duck_genuine/article/details/6903300 2. 拼写检查 (spellCheck) 配置solrconfig.xml 3. 匹配相似(moreLikeThis) 在 solrconfig.xml 中配置 MoreLikeThisHandler 参考: http://bastengao.iteye.com/blog/1197651 4. Solrconfig配置,searchComponent及requestHandler 其余solrconfig.xml配置,参照:http://blog.duteba.com/seo/article/67.htm 5. 对拼音的搜索 http://blog.csdn.net/xiaozhengdong/article/details/7045402 6. 优化: http://blog.csdn.net/flanet/article/details/7834803

下载文档到电脑,查找使用更方便

文档的实际排版效果,会与网站的显示效果略有不同!!

需要 8 金币 [ 分享文档获得金币 ] 0 人已下载

下载文档