solr 搜索 流程 分析

以单机搜索为例,暂不考虑分布式搜索

分析版本为: lucene_solr_branch_4x

配置文件solrconfig.xml

       在solr启动的过程中加载solrconfig.xml,初始化文件中定义的信息,如处理请求的handler。

 <requestHandler name="/select" class="solr.SearchHandler">
    <!-- default values for query parameters can be specified, these
         will be overridden by parameters in the request
      -->
     <lst name="defaults">
       <str name="echoParams">explicit</str>
       <int name="rows">10</int>
       <str name="df">text</str>
     </lst>
 
 </requestHandler>


启动solr,发送请求:

http://localhost:8983/core1/select?q=id:GB18030TEST&wt=xml

       由core1处理查询请求,查询id=GB18030TEST 的doc,并以xml格式返回


请求分发器SolrDispatchFilter

      当一个查询请求过来时,先到类SolrDispatchFilter-->doFilter(),由这个分发器中的dofilter()方法进行解析请求URL,

core = cores.getCore(corename);

根据url可以获得corename=“core1”  即使用core1进行处理查询请求,path="/select"  即请求请求对应的处理handler是"/select"。

final SolrConfig config = core.getSolrConfig();

获取core1对应的solrconfig信息。


handler = core.getRequestHandler( path );

获取"/select"对应的RequestHandler。


this.execute( req, handler, solrReq, solrRsp );

将请求请求和相关信息交由SolrDispatchFilter-->execute()处理


    sreq.getContext().put( "webapp", req.getContextPath() );
    sreq.getCore().execute( handler, sreq, rsp );
这里将会调用SolrCore类的 execute()方法,是solrCore留下的接口来处理请求的。

进入SolrCore类

先向SolrQueryResponse中添加一些响应首部的一些信息,

handler.handleRequest(req,rsp);
将处理权交由RequestHandlerBase-->handleRequest()进一步处理。

进入RequestHandlerBase

handleRequestBody( req, rsp );
将处理权交由 RequestHandlerBase子类:SearchHandler-->handleRequestBody()进一步处理

进入 SearchHandler类

      for( SearchComponent c : components ) {
        c.prepare(rb);
      }
遍历solrconfig中配置的searchhandler的各个组件,调用各个组件的prepare()方法

        // Process
        for( SearchComponent c : components ) {
          c.process(rb);
        }
调用各个组件的process()方法,运行组件,将获取的信息添加到ResponseBuilder对象中。该次查询有QueryComponent、FacetComponent、MoreLikeThisComponent、HighlightComponent、 StatsComponent、DebugComponent这几个组件参与。


以查询组件为例

        QueryComponent-->process(ResponseBuilder rb)

    // normal search result
    searcher.search(result,cmd);
    rb.setResult( result );
   将查询结果添加到 ResponseBuilder对象中,然后返回,具体查询细节,可以跟踪调试下,这里不再陈述。


结尾

  以上执行完以后,返回到SolrDispatchFilter-->doFilter()执行以下程序:

               QueryResponseWriter responseWriter = core.getQueryResponseWriter(solrReq);
               writeResponse(solrRsp, response, responseWriter, solrReq, reqMethod);
将返回结果以xml的形式返回


      finally {
        if( solrReq != null ) {
          solrReq.close();
        }
        if (core != null) {
          core.close();
        }
        SolrRequestInfo.clearRequestInfo();        
      }
结束操作,清除solrreq和core对象实例,剩下交由 jetty来善后了。


网上有篇NB的分析文章:http://blog.csdn.net/duck_genuine/article/details/6962624讲得相当不错。


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值