PHP实现全文索引,使用讯搜(官方网站http://www.xunsearch.com/)
1.安装
目前讯搜只能安装在linux系统,官方安装文档:http://www.xunsearch.com/doc/php/guide/start.installation
安装步骤:
# 下载安装包
wget http://www.xunsearch.com/download/xunsearch-full-latest.tar.bz2
# 解压 如果报错tar (child): lbzip2: Cannot exec: No such file or directory 则安装bzip2,执行命令: yum -y install bzip2
tar -xjf xunsearch-full-latest.tar.bz2
# 安装
cd xunsearch-full-1.3.0/
sh setup.sh
# 中途需要输入安装路径,我这边的安装路径是 /opt/www/xunsearch,记得先创建好路径
# 安装完成会提示启动命令,其实就是安装路径下bin/xs-ctl.sh restart
# 启动服务
/opt/www/xunsearch/bin/xs-ctl.sh restart
启动完成后可以输入命令查看服务的运行状态: ps -ef | grep xs-searchd
安装完成
2.PHP使用讯搜
首先创建数据库配置文件,官方建议我们数据库配置文件都统一放在安装路径下/sdk/php/apk/下,我这边创建一个新闻数据库:
/opt/www/xunsearch/sdk/php/apk/news.ini
内容如下:
project.name = news
project.default_charset = utf-8
server.index = 8383
server.search = 8384
[pid]
type = id
[subject]
type = title
[message]
type = body
[chrono]
type = numeric
代码中调用讯搜的逻辑是:
(1)新增索引
(2)搜索
代码中调用讯搜必须引入/opt/www/xunsearch/sdk/php/lib/XS.php,下面是新增索引的代码例子:
<?php
require_once '/opt/www/xunsearch/sdk/php/lib/XS.php';
try{
$xs = new XS('/opt/www/xunsearch/sdk/php/apk/news.ini');
$index = $xs->index;
$doc = new XSDocument;
// 添加文章1的索引
$doc->setFields(array(
'pid' => 1, // 唯一ID
'subject' => '炸带鱼时,拍面粉还是淀粉?原来很多人都做错了,这才是正确方法', // 文章标题
'message' => '', // 内容 因为我这边只希望根据标题搜索,所以内容为空
'chrono' => time() // 设置这个值后面排序用到
));
$index->add($doc);
// 添加文章2的索引
$doc->setFields(array(
'pid' => 2,
'subject' => '戒烟那么难,为什么还是劝你试?这些好处一个月就能体现',
'message' => '',
'chrono' => time()
));
$index->add($doc);
}catch(XSException $e) {
print_r($e);
}
搜索代码例子:
<?php
require_once '/opt/www/xunsearch/sdk/php/lib/XS.php';
try{
$xs = new XS('/opt/www/xunsearch/sdk/php/apk/news.ini');
// setFuzzy 开启模糊搜索,让搜索结果更加广泛
// setSort('chrono') 设置排序为chrono值倒序
// setLimit(10, 5) 获取结果最大10条,从第5条开始
// search('世界') 搜索关键词
$docs = $xs->search->setFuzzy()->setSort('chrono')->setLimit(10, 5)->search('世界');
}catch(XSException $e) {
print_r($e);
}
获取分词代码例子:
<?php
require_once '/opt/www/xunsearch/sdk/php/lib/XS.php';
try{
$xs = new XS('/opt/www/xunsearch/sdk/php/apk/news.ini');
$xs_token = new XSTokenizerScws();
return $xs_token->getResult('炸带鱼时,拍面粉还是淀粉?原来很多人都做错了,这才是正确方法');
}catch(XSException $e) {
print_r($e);
}
更多的功能参考官方文档http://www.xunsearch.com/doc/php/guide/start.overview , http://www.xunsearch.com/doc/php/api
下面是实际开发应用整理的使用讯搜的工具类:
<?php
require_once '/opt/www/xunsearch/sdk/php/lib/XS.php';
class MyXS {
protected $xs;
protected $xs_doc;
protected $xs_token;
function __construct() {
$this->xs = new XS(dirname(__FILE__) . DIRECTORY_SEPARATOR . 'news.ini');
$this->xs_doc = new XSDocument;
$this->xs_token = new XSTokenizerScws;
}
/* 添加索引 */
public function addIndex($pid, $subject, $chrono = null) {
$this->xs_doc->setFields(array(
'pid' => $pid,
'subject' => $subject,
'message' => '',
'chrono' => empty($chrono) ? time() : $chrono
));
$this->xs->index->add($this->xs_doc);
}
/* 搜索 */
public function search($key, $step = 20, $start = 0) {
$docs = $this->xs->search->setFuzzy()->setSort('chrono')->setLimit($step, $start)->search($key);
$result = array();
foreach ($docs as $key => $value) {
$result[$value['pid']] = $value['subject'];
}
return $result;
}
/* 分词 */
public function getToken($str) {
$result = $this->xs_token->getResult($str);
$token = array();
foreach ($result as $key => $value) {
$token[] = $value['word'];
}
return $token;
}
/* 清空索引 */
public function clearIndex() {
$this->xs->index->clean();
}
}