Skip to content


Sphinx+Mysql+中文分词安装-实现中文全文搜索

什么是Sphinx
Sphinx 是一个在GPLv2 下发布的一个全文检索引擎,商业授权(例如, 嵌入到其他程序中)
需要联系我们(Sphinxsearch.com)以获得商业授权。
一般而言,Sphinx是一个独立的搜索引擎,意图为其他应用提供高速、低空间占用、高结果
相关度的全文搜索功能。Sphinx可以非常容易的与SQL数据库和脚本语言集成。
当前系统内置MySQL和PostgreSQL 数据库数据源的支持,也支持从标准输入读取特定格式
的XML数据。通过修改源代码,用户可以自行增加新的数据源(例如:其他类型的DBMS
的原生支持)。
搜索API支持PHP、Python、Perl、Rudy和Java,并且也可以用作MySQL存储引擎。搜索
API非常简单,可以在若干个小时之内移植到新的语言上。
Sphinx 是SQL Phrase Index的缩写,但不幸的和CMU的Sphinx项目重名

Sphinx的特性

  • 高速的建立索引(在当代CPU上,峰值性能可达到10 MB/秒);
  • 高性能的搜索(在2 – 4GB 的文本数据上,平均每次检索响应时间小于0.1秒);
  • 可处理海量数据(目前已知可以处理超过100 GB的文本数据, 在单一CPU的系统上可
    处理100 M 文档);
  • 提供了优秀的相关度算法,基于短语相似度和统计(BM25)的复合Ranking方法;
  • 支持分布式搜索;
  • provides document exceprts generation;
  • 可作为MySQL的存储引擎提供搜索服务;
  • 支持布尔、短语、词语相似度等多种检索模式;
  • 文档支持多个全文检索字段(最大不超过32个);
  • 文档支持多个额外的属性信息(例如:分组信息,时间戳等);
  • 停止词查询;
  • 支持单一字节编码和UTF-8编码;
  • 原生的MySQL支持(同时支持MyISAM 和InnoDB );
  • 原生的PostgreSQL 支持.

一、安装所需文件
mmseg-0.7.3.tar.gz 中文分词
http://www.coreseek.com/uploads/sources/mmseg-0.7.3.tar.gz

mysql-5.1.26-rc.tar.gz mysql-5.1.26源代码

sphinx-0.9.8-rc2.tar.gz sphinx-0.9.8-rc2源代码
http://www.sphinxsearch.com/downloads/sphinx-0.9.8-rc2.tar.gz

fix-crash-in-excerpts.patch sphinx支持分词补丁
http://www.coreseek.com/uploads/sources/fix-crash-in-excerpts.patch

sphinx-0.98rc2.zhcn-support.patch sphinx支持分词补丁
http://www.coreseek.com/uploads/sources/sphinx-0.98rc2.zhcn-support.patch

二、开始安装
1.安装libmmseg


tar -zxvf mmseg-0.7.3.tar.gz
cd mmseg-0.7.3
./configure –prefix=/usr/local/mmseg
make
make install
cd ..

安装mmseg完成,测试一下

mmseg
Coreseek COS(tm) MM Segment 1.0
Copyright By Coreseek.com All Right Reserved.
Usage: mmseg

有问题可以尝试执行下面命令

echo ‘/usr/local/mmseg/lib’ >> /etc/ld.so.conf
ldconfig -v
ln -s /usr/local/mmseg/bin/mmseg /bin/mmseg

=================2011-08-26 更新=================

在centos6 g++4.4.4上编辑错误

css/UnigramCorpusReader.cpp: In member function ‘virtual int css::UnigramCorpusReader::open(const char*, const char*)’:
css/UnigramCorpusReader.cpp:89: error: ‘strncmp’ was not declared in this scope
make[2]: *** [UnigramCorpusReader.lo] Error 1
make[2]: Leaving directory `/root/src/sphinx/mmseg-0.7.3/src’
make[1]: *** [all-recursive] Error 1
make[1]: Leaving directory `/root/src/sphinx/mmseg-0.7.3′
make: *** [all] Error 2

解决方法
vi .src/css/UnigramCorpusReader.cpp
第一行加上

#include

然后重新 make
===================================================

2.重新编译mysql
在安装之前先打两个补丁,这个是支持中文必须打的补丁

tar -zxvf sphinx-0.9.8-rc2.tar.gz
cd sphinx-0.9.8
patch -p1 < ../sphinx-0.98rc2.zhcn-support.patch patch -p1 < ../fix-crash-in-excerpts.patch

之前我已安装了mysql5.1.26,这里略过具体安装步骤
mysql编译路径
/root/lemp/mysql-5.1.26-rc/
mysql安装路径
/opt/mysql

安装之前关闭mysql

/opt/mysql/bin/mysql.server stop

接着将sphinx下的mysqlse 文件夹下的数据拷贝到mysql-5.1.26-rc/storage/sphinx 下面
(这样才能在编译mysql的时候把SphinxSE存储引擎编译进去)

cp -rf mysqlse /root/lemp/mysql-5.1.26-rc/storage/sphinx
cd /root/lemp/mysql-5.1.26-rc

make clean
sh BUILD/autorun.sh
#这步是必须的,请勿遗漏

开始重新编译

CFLAGS=”-O3″ CXX=gcc CXXFLAGS=”-O3 -felide-constructors -fno-exceptions -fno-rtti” ./configure –prefix=/opt/mysql –localstatedir=/opt/mysql/var –sysconfdir=/opt/mysql –without-debug –with-unix-socket-path=/opt/mysql/mysql.sock –with-big-tables –with-charset=gbk –with-collation=gbk_chinese_ci –with-client-ldflags=-all-static –with-mysqld-ldflags=-all-static –enable-assembler –with-extra-charsets=gbk,gb2312,utf8 –with-pthread –enable-thread-safe-client –with-innodb –with-plugins=sphinx
make
make install


configure: error: unknown plugin: sphinx

我的解决方法:
重新解压一份mysql source
在执行autorun.sh前修改storage/sphinx的用户和用户组,还有权限
sh BUILD/autorun.sh
./configure -h
查看最低下有否包含了sphinx

=== Sphinx Storage Engine ===
Plugin Name: sphinx
Description: Sphinx Storage Engines
Supports build: static and dynamic
Configurations: max, max-no-ndb

然后再编译

make时错误

../libtool: line 466: CDPATH: command not found
../libtool: line 1144: func_opt_split: command not found
libtool: Version mismatch error. This is libtool 2.2.6, but the
libtool: definition of this LT_INIT comes from an older release.
libtool: You should recreate aclocal.m4 with macros from libtool 2.2.6
libtool: and run autoconf again.
make[1]: *** [conf_to_src] 错误 63
make[1]: Leaving directory `/home/andychu/lemp2/mysql-5.1.26-rc/strings’
make: *** [all-recursive] 错误 1

libtool版本不一至产生错误,可以将已安装的libtool覆盖到编译目录
cp /usr/local/bin/libtool .
再重新编译

编译完成,启动mysql,检查SphinxSE存储引擎是否编译进去

/opt/mysql/bin/mysql.server start
/opt/mysql/bin/mysql -uroot -p

Mysql>
输入
show engines;

+————+———+———————————————————–+————–+—-+————+
| Engine | Support | Comment | Transactions | XA | Savepoints |
+————+———+———————————————————–+————–+—-+————+
| CSV | YES | CSV storage engine | NO | NO | NO |
| SPHINX | YES | Sphinx storage engine 0.9.8 | NO | NO | NO |
| MEMORY | YES | Hash based, stored in memory, useful for temporary tables | NO | NO | NO |
| MyISAM | DEFAULT | Default engine as of MySQL 3.23 with great performance | NO | NO | NO |
| MRG_MYISAM | YES | Collection of identical MyISAM tables | NO | NO | NO |
+————+———+———————————————————–+————–+—-+————+
5 rows in set (0.00 sec)

此时我们可以看到已经包含sphinxSE 引擎

3.安装sphinx

cd /root/lemp/sphinx-0.9.8-rc2
./configure –prefix=/usr/local/sphinx –with-mysql=/opt/mysql \
–with-mysql-includes=/opt/mysql/include/mysql –with-mysql-libs=/opt/mysql/lib/mysql \
–with-mmseg-includes=/usr/local/mmseg/include –with-mmseg-libs=/usr/local/mmseg/lib –with-mmseg
make

头文件没找到:

tokenizer_zhcn.cpp:1:30: SegmenterManager.h: 没有那个文件或目录
tokenizer_zhcn.cpp:2:23: Segmenter.h: 没有那个文件或目录


make clean
./configure –prefix=/usr/local/sphinx –with-mysql=/opt/mysql \
–with-mysql-includes=/opt/mysql/include/mysql –with-mysql-libs=/opt/mysql/lib/mysql \
–with-mmseg-includes=/usr/local/mmseg/include/mmseg –with-mmseg-libs=/usr/local/mmseg/lib –with-mmseg


/root/sphinx/sphinx-0.9.8-rc2/src/tokenizer_zhcn.cpp:34: undefined reference to `libiconv_close’
collect2: ld returned 1 exit status

官网解决办法:
In the meantime I’ve change the configuration file and set
#define USE_LIBICONV 0 in line 8179.
修改configure 文件把 #define USE_LIBICONV 0 最后的数值由1改为0
重新编译。


make clean
./configure –prefix=/usr/local/sphinx –with-mysql=/opt/mysql \
–with-mysql-includes=/opt/mysql/include/mysql –with-mysql-libs=/opt/mysql/lib/mysql \
–with-mmseg-includes=/usr/local/mmseg/include/mmseg –with-mmseg-libs=/usr/local/mmseg/lib –with-mmseg

vi configure
输入/define USE_LIBICONV 找到目标行
按i键后将1改成0,按esc,输入:wq保存退出

make
make install

编译时报如下的错误
/usr/local/include/mmseg/freelist.h:22: error: ‘strlen’ was not declared in this scope
vi /usr/local/include/mmseg/freelist.h
或者这个地址
vi /usr/local/mmseg/include/mmseg/freelist.h
加上

#include

再次编译就不会报错了。

复制一份sphinx的配置

cd /usr/local/sphinx/etc
cp sphinx.conf.dist sphinx.conf

4.配置sphinx

修改/usr/local/sphinx/etc/sphinx.conf

type = mysql
# some straightforward parameters for SQL source types
sql_host = localhost
sql_user = root
sql_pass =
sql_db = test
sql_port = 3306 # optional, default is 3306

address = 127.0.0.1 #安全点可以只监听本机

5.索引建立

装好sphinx后在sphinx的目录中有三个目录 分别为bin etc var
bin中 存有sphinx用到的一些执行文件 包括 indexer 索引建立 search 查询工具 searchd 查询服务器 等

为了下面测试方便,我们先将sphinx.conf自带的example.sql脚本倒入的mysql中
//创建了一个test库,并建立了documents测试表和数据

/opt/mysql/bin/mysql -uroot -p < /usr/local/sphinx/etc/example.sql

索引的建立方法为

/usr/local/sphinx/bin/indexer –config /usr/local/sphinx/etc/sphinx.conf test1

test1为资源名称 不写为默认所有都建立索引
附:
建立索引期间可能由于不同版本的数据库导致indexer找不到共享库libmysqlclient.so.16
需要把/opt/mysql/lib/mysql/libmysqlclient.so.16.0.0 这个文件复制到/usr/lib下 或者作软连接即可

6.查询服务器

/usr/local/sphinx/bin/searchd –config /usr/local/sphinx/etc/sphinx.conf 为开启

/usr/local/sphinx/bin/searchd –config /usr/local/sphinx/etc/sphinx.conf –stop 为关闭

sphinx的查询 可以大致分为三种

1 数据库引擎中的查询

2 通过search工具查询
/usr/local/sphinx/bin/search –config /usr/local/sphinx/etc/sphinx.conf test

3 通过php的接口查询 详见sphinxapi.php.

三、在mysql中的使用SphinxSE方式调用Sphinx

1.在mysql中的使用SphinxSE方式调用Sphinx
首先建立一张索引专用表:

CREATE TABLE `sphinx` (
`id` int(11) NOT NULL,
`weight` int(11) NOT NULL,
`query` varchar(255) NOT NULL,
`CATALOGID` INT NOT NULL,
`EDITUSERID` INT NOT NULL,
`HITS` INT NULL,
`ADDTIME` INT NOT NULL, KEY
`Query` (`Query`)
) ENGINE=SPHINX DEFAULT CHARSET=utf8 CONNECTION=’sphinx://localhost:3312/test1′

test1:索引的名称,可以在sphinx.conf中查找到
建立完索引专用表后,我们就可以在mysql中使用它了,例如,在mysql中输入

SELECT doc. * FROM documents doc JOIN sphinx ON ( doc.id = sphinx.id ) WHERE query = ‘doc;mode= any’

运行后,结果记录中将会显示包含doc字符串的所用记录行

关于query的语法,还有sphinx的配置等信息你可以请参考:
http://www.sphinxsearch.com/doc.html

2.中文分词应用
生成词典
进入到mmseg的源代码目录后

cd data
mmseg -u unigram.txt

在data下边会产生一个文件unigram.txt.uni
这个就是生成的字典 然后把字典改名为uni.lib放在可以读取的目录中即可

cp unigram.txt.uni /usr/local/sphinx/uni.lib

修改 sphinx.conf(/usr/local/sphinx/etc/sphinx.conf)配置文件
在索引中加入

charset_type = zh_cn.utf-8
charset_dictpath = /usr/local/sphinx/

数据库中增加一条中文数据

INSERT INTO `test`.`documents` (
`id` ,
`group_id` ,
`group_id2` ,
`date_added` ,
`title` ,
`content`
)
VALUES (
NULL , ‘3’, ‘9’, NOW( ) , ‘sphinx中文搜索’, ‘Sphinx是一个基于SQL的全文检索引擎,可以结合MySQL,PostgreSQL做全文搜索,它可以提供比数据库本身更专业的搜索功能,使得应用程序更容易实现专业化的全文检索。Sphinx特别为一些脚本语言设计搜索API接口,如PHP,Python,Perl,Ruby等,同时为MySQL也设计了一个存储引擎插件。 ‘
);

(如果searchd已经再运行,先kill 它再运行)
注意:在添加完数据后,需要重新加载索引,这样新的数据才能被缓存进去
重建索引,成功后,开启索引监听

/usr/local/sphinx/bin/indexer –config /usr/local/sphinx/etc/sphinx.conf –all
/usr/local/sphinx/bin/searchd –config /usr/local/sphinx/etc/sphinx.conf

在ide硬盘上建索引的速度

indexing index ‘test1’…
collected 423228 docs, 637.2 MB
sorted 125.5 Mhits, 100.0% done
total 423228 docs, 637201412 bytes
total 753.401 sec, 845766.13 bytes/sec, 561.76 docs/sec

这样,就可以在phpmyadmin中进行测试了。

SELECT doc. * FROM documents doc JOIN sphinx ON ( doc.id = sphinx.id )
WHERE query = ‘设计;mode= any ‘

好像没出来。。。。

修改 sphinx.conf
去掉下面的注释

sql_query_pre = SET NAMES utf8

再重启searchd就可以搜出结果了

参考:
http://www.coreseek.com/uploads/pdf/sphinx_doc_zhcn_0.9.pdf
http://www.sphinxsearch.com/wiki/doku.php?id=sphinx_chinese_tutorial
http://www.cnblogs.com/hushixiu/articles/1295605.html
http://blog.xoyo.com/dcyhldcyhl/article/839863.shtml
http://blog.sina.com.cn/s/blog_5aefd9770100axf1.html
http://blog.s135.com/post/360/

2009-06-28更新
编码的解决方法(未经测试)
——————————————————————————-
转换现有表的数据
iconv -f GB18030 -t utf-8 -o dump.sql dump_utf8.sql

也可以不转换,直接使用现有的GBK的数据,但是需要设置连接方式
mysql_query(“SET character_set_client = ‘gbk'”, $conn);
mysql_query(“SET character_set_connection =’gbk'”, $conn); //设置character_set_connection也就同时设置了collation_connection
//mysql_query(“SET collation_connection = ‘gbk'”, $conn);
mysql_query(“SET character_set_results =’utf8′”, $conn);
这三个设置后,查询得到的结果,就是UTF8编码的结果了。合适给SPHINX使用。

mysql_query(“SET SESSION query_cache_type=OFF”, $conn);
//indexer建立索引时的查询,不需要缓存的
——————————————————————————-

2009-06-28更新
coreseek网站好像出问题不能下载咯。
提供安装部分文件下载,共3.6M,包含以下文件
build_delta_index.sh
build_main_index.sh
fix-crash-in-excerpts.patch
mmseg-0.7.3.tar.gz
sphinx-0.9.8-rc2.tar.gz
sphinx-0.98rc2.zhcn-support.patch
sphinx.conf
sphinxapi.php
test.php
test2.php

>>猛击这里下载sphinx安装文件

——————————————————————————-

2009-06-28更新
使用service 控制sphinx
先增加一sphinx用户并属于website组(事先已存在),并修改sphinx目录的属主

useradd -d /usr/local/sphinx -g website -s /sbin/nologin sphinx
chown -R sphinx:website /usr/local/sphinx

创建/etc/init.d/sphinx脚本

#!/bin/sh
# sphinx: Startup script for Sphinx search
#
# chkconfig: 345 86 14
# description: This is a daemon for high performance full text \
# search of MySQL and PostgreSQL databases. \
# See http://www.sphinxsearch.com/ for more info.
#
# processname: searchd
# pidfile: $sphinxlocation/var/log/searchd.pid

# Source function library.
. /etc/rc.d/init.d/functions

processname=searchd
servicename=sphinx
username=sphinx
sphinxlocation=/usr/local/sphinx
pidfile=$sphinxlocation/var/log/searchd.pid
searchd=$sphinxlocation/bin/searchd

RETVAL=0

PATH=$PATH:$sphinxlocation/bin

start() {
echo -n $”Starting Sphinx daemon: ”
daemon –user=$username –check $servicename $processname
RETVAL=$?
echo
[ $RETVAL -eq 0 ] && touch /var/lock/subsys/$servicename
}

stop() {
echo -n $”Stopping Sphinx daemon: ”

$searchd –stop
#killproc -p $pidfile $servicename -TERM
RETVAL=$?
echo
if [ $RETVAL -eq 0 ]; then
rm -f /var/lock/subsys/$servicename
rm -f $pidfile
fi
}

# See how we were called.
case “$1″ in
start)
start
;;
stop)
stop
;;
status)
status $processname
RETVAL=$?
;;
restart)
stop
sleep 3
start
;;
condrestart)
if [ -f /var/lock/subsys/$servicename ]; then
stop
sleep 3
start
fi
;;
*)
echo $”Usage: $0 {start|stop|status|restart|condrestart}”
;;
esac
exit $RETVAL

修改权限并加入到service,机器启动时自动启动

chmod 755 /etc/init.d/sphinx
chkconfig –add sphinx
chkconfig –level 345 sphinx on
chkconfig –list|grep sphinx #检查下


service sphinx start #运行
service sphinx stop #停止,官方的脚本在我的as4上有点问题,所以粗鲁的改了下
service sphinx restart #重启
service sphinx status #查看是否运行

检查下已用sphinx用户运行

ps aux |grep searchd
sphinx 24612 0.0 0.3 11376 6256 pts/1 S 14:07 0:00 searchd

>>猛击这里下载sphinx启动脚本

参考:http://www.sphinxsearch.com/wiki/doku.php?id=for_centos_5
http://www.notsofaqs.com/catsdoc/doku.php?id=sphinx:install

Posted in sphinx, 技术.

Tagged with , , .


9 Responses

Stay in touch with the conversation, subscribe to the RSS feed for comments on this post.

  1. bbayou says

    强大!!!!谢谢!!!!最近也在研究这个东西!!!

  2. 格子 says

    如何在windows上面安装啊??

  3. sphinx says

    你好,我想问下你建立的那个 sphinx 表的内容从哪里来呢?

  4. C1G says

    /usr/local/sphinx/etc/example.sql
    测试数据是自已填的

  5. iterse's blog says

    总结的很全,谢谢分享。遇到的问题都解决了,就是在更新documents中的内容时(更新前将searchd kill掉了),更新后重新建立索引,在查询的时候没有相应的结果,请博主指点下,谢谢!我的mail:xinghonggui@120.net

Continuing the Discussion

  1. 大碗茶馆 » 自己总结了一下CentOS 5.3,5.4 下nginx+php(fastcgi)+mysql+sphinx(coreseek)的安装步骤 linked to this post on 2009/12/18

    […] 编译PHP-FPM 0.6 for PHP 5.2.11 + Sohusin补丁 Sphinx+Mysql+中文分词安装-实现中文全文搜索 等… 发表评论 | Trackback 暂无相关日志 […]

  2. 中文全文搜索 sphinx+ mysql+ mmseg 安装,配置,调用 | auu linked to this post on 2010/12/04

    […] 参考:http://blog.c1gstudio.com/archives/722 http://www.zhengjinjun.com/index.php/2009/06/28/sphinxmysql http://www.htmldata.cn/?p=171 mysqlphpsearchserver CATEGORIES […]



Some HTML is OK

or, reply to this post via trackback.