solr使用实例、solr结合mysql生成索引

  • 内容
  • 评论
  • 相关

之前有篇文章是讲述如何搭建solr的,搭建结束之后呢,我们需要简单的使用一下solr,其中solr提供了很多的客户端语言,在这里我们以php为例,简单的讲一下如何建立索引和进行搜索。
首先给出一段小例子的程序,我们使用的是solrphpclient的封装类库,第三方的solr处理类库还有solarium,也是很棒的一款类库。

<?php
require_once('Apache/Solr/Service.php' );
// 连接solr服务器
$solr = new Apache_Solr_Service('127.0.0.1', '8080', '/solr');
/**如果是多核的话,想连接到某个核心,其实也就是将索引文件存放在哪里,多核的配置查看http://www.xiaotiejiang.com/archives/240
$solr = new Apache_Solr_Service('127.0.0.1', '8080', '/solr/core0');
**/
//测试是否联通
if (!$solr->ping()) {
    echo 'Solr service not responding.';
    exit;
}

$parts = array(
    'group1' => array(
        'id' => 1,
        'name' => 'hellogxp',
        'address' => 'hangzhou',
//      'address' => array( 'tiananmen', 'fdrfr' ),
    ),
    'group2' => array(
        'id' => 2,
        'name' => 'xuguang',
        'address' => 'taizhou',
    ),
    'group3' => array(
        'id' => 3,
        'name' => 'aliang',
        'address' => 'shaoxing',
    ),
    'group4' => array(
        'id' => 4,
        'name' => 'liqiong',
        'hobby' => array('swimming','reading','music'),
    )
);

foreach ($parts as $item => $fields) {
    $part = new Apache_Solr_Document();
    foreach ($fields as $key => $value) {
        if (is_array($value)) {
            foreach ($value as $datum) {
                $part->setMultiValue($key, $datum);
            }
        } else {
            $part->$key = $value;
        }
    }
    $documents[] = $part;
}
//var_dump($documents);

// 创建索引
try {
    $solr->addDocuments($documents);
    $solr->commit();
    $solr->optimize();
} catch (Exception $e) {
    echo $e->getTraceAsString();
}

$offset = 0;
$limit = 10;
$queries = array(
    'id: 1 OR id: 2',
    'name: hellogxp',
    'address: shaoxing',
    'hobby:swimming'
);
foreach ($queries as $query) {
    $response = $solr->search($query, $offset, $limit,array('sort'=>'id desc'));
    if ($response->getHttpStatus() == 200) {
        if ($response->response->numFound > 0) {
            foreach ($response->response->docs as $doc) {
                //注意,在solr中的查询出的数据可以自由组装,例如下面就是将查询出的个人信息封装成数组,然后给$doc变量新建一个数组对象profile
                $doc->profile = array(
                    'name'=> $doc->name,
                    'address'=> $doc->address,
                    'id'=> $doc->id,
                );
                $info[] = $doc->profile;
                //echo "$doc->address $doc->name <br />";
            }
            echo '<br />';
        }
        print_r($info);
    } else {
        echo $response->getHttpStatusMessage();
    }
}
?>

这里有个小问题,solr提供了这么强大功能,包括相似搜索(类似一些踩你喜欢,您是不是要找……之类的功能可以用到),分词功能。我么这里简单说一下solr的排序,我们先来通过solr admin来看一下,正常的solr admin的web端你会看到:http://localhost:8080/solr/select/?q=*%3A*&version=2.2&start=0&rows=10,其实我们只需要一个参数即可,在url后面加一个get参数field desc,这样子便会按照这个字段的降序排列http://localhost:8080/solr/select/?q=*%3A*&version=2.2&start=0&rows=10&sort=products_date_added%20desc,多个字段排序使用,隔开&srot=field1 desc,field2 desc,按field1字段降序排列,如果字段值相同时,再按field2字段降序排列api当中实现我们在search函数中加一个数组即可array('sort'=>'id desc')。当然,如果一个字段你设置为text,就不能参与排序了,因为这个都被分词了,因此不能被作为查询排序的字段使用。没有指定 sort 参数时,搜索结果默认按文档得分(score)的降序。(desc)排列。还有一个问题就是索引的更新和重建,当你有数据更新的时候,可以进行部分更新而不需要每次都重建索引,例如你有一条数据需要更新,那么直接使用solr的add/update或者使用phpsorclient进行这一条数据的更新, 其实你使用add也不会有问题,因为在add时候solr会根据你的unique id检查数据,如果已经存在就更新,不存在就新建。
这里需要编辑solr的配置文件,我的solr安装在tomcat下面,/usr/local/tomcat/solr/conf/schema.xml
在文件

<fields>
<field name="id" type="string" indexed="true" stored="true" required="true" />
<field name="name" type="string" indexed="true" stored="true" required="true" />
<field name="address" type="string" indexed="true" stored="true" required="true"  />
<field name="hobby" type="string" multiValued="true" indexed="true" stored="true"/>
</fields>

其中name字段不能重名。然后重启tomcat。这里注意一下,其中hobby字段有个属性multiValued设置为了true,这是因为本身原始数组中hobby这个字段就是一个数组。至于这个schemaxml中的字段的type,我们可以参考官方文档:http://wiki.apache.org/solr/SchemaXml。
刚才我们建立索引是使用的solrphpclient类,鉴于我们很多项目都是使用mysql作为关系数据库存储数据,那么我们现在讲一下如何结合solr和mysql直接将mysql中的数据生成索引。
首先solr要和mysl通信,我们使用Mysql JDBC,这个类的名字为;com.mysql.jdbc.Driver。调用URL方式为:

URL:jdbc:mysql://servername:port/database

那么我们先下载mysql-connector-java-5.1.22-bin.jar,然后将这个文件复制到solr根目录的lib文件夹下(这个文件夹需要手动创建),我的环境下是/opt/solr/example/solr/lib这个目录。
那么除了这个插件外,我们还需要DIH,也就是dataImportHandler,这个插件是solr用来导入数据生成索引的,因此我们需要下载apache-solr-dataimporthandler-extras-3.6.1.jar和apache-solr-dataimporthandler-3.6.1.jar。这两个文件我们同样复制到/usr/local/tomcat/solr/lib这个文件夹下。
okay工具和类库已然准备好了,下面我们开始修改和创建配置文件。
首先我们需要来定义一下solr和mysql的通信,我们先修改/usr/local/tomcat/solr/conf/solrconfig.xml文件。

vim  /usr/local/tomcat/solr/conf/solrconfig.xml

在其中加入

<requestHandler name="/dataimport" class="org.apache.solr.handler.dataimport.DataImportHandler">
<lst name="defaults">
  <str name="config">data-config.xml</str>
</lst>
</requestHandler>

这个文件的作用是定义data-config.xml文件的路径,data-config.xml这个文件就是定义solr和mysql通信的相关信息。当然data-config.xml这个文件需要我们手动添加。

cd /usr/local/tomcat/solr/conf
vim data-config.xml

在这个新建的文件中添加:

<dataConfig>
  <dataSource type="JdbcDataSource" 
              driver="com.mysql.jdbc.Driver"
              url="jdbc:mysql://localhost/demo" 
              user="root" 
              password="password"/>
  <document>
    <entity name="id" 
            query="select name from demo">
    </entity>
  </document>
</dataConfig>

这个文件的信息很明显,在此不做解释。
还有一点就是如果你的数据库中查询的字段没有在shcema.xml中定义,需要先去shcema.xml定义,这个在本文有所提过,非常简单,就是添加一个字段而已。
之后我们重启tomcat,

/usr/local/tomcat/bin/shutdown.sh
/usr/local/tomcat/bin/startup.sh

接下来,我们就可以测试一下索引生成的效果了:

http://localhost:8080/solr/dataimport?command=full-import

这个表示生成新索引并且删除旧的索引,如果不删除旧的索引,可以这样:

http://localhost:8080/solr/dataimport?command=full-import&clean=false

有一点需要注意的是,solr的索引生成是增量生成方式,也就是说如果你生成索引之前不去删除上次的索引,那么本次的索引生成将会按照唯一ID进行更新操作,如果你本次生成的数据中删除了一条,那么如果你不将上次的索引全删掉就进行索引生成,那么这条删除掉的数据还会存在,我们可以通过solr的web端进行删除:

http://xiaotiejiang.com:8080/solr/core_1/update/?stream.body=<delete><id>123456</id></delete>&stream.contentType=text/xml;charset=utf-8&commit=true

这样你就根据唯一id删除掉了一条数据。
但是如果你的新数据中有很多删除掉的,那么不可能这样一条一条的删掉(当然,如果你愿意,可以使用curl来批量处理),我们就需要删掉data下面的所有文件夹,这时候如果你再生成也许会报错,因为这时候你需要重启tomcat服务,重启之后在data下面会重新自动生成index和spellchecker文件夹,并且index文件夹下会有文件生成( 因此即使你自己手动建立这两个文件夹也是不行的,必必须要由服务自动建立)。因此记得如果删掉索引文件重建索引,需要重启tomcat服务。
最后提及一点,solr的索引文件是在/op/solr/example/solr/data/下的index文件夹(如果你的solr是配置的多核心的就在solr/cores/core1/data/index下面),data下的文件在建立索引的时候都会自动建立。
这时候你可以从页面xml文档得到信息,例如就生成了多少条索引等。你可以使用solradmin来查看一下结果:

http://localhost:8080/solr/admin

可以在其中输入关键字查询一下。
注:本文的所有路径都是本机安装目录和路径,具体实践请参阅自己的软体安装路径。

评论

0条评论

发表评论

您的电子邮箱地址不会被公开。 必填项已用*标注