您的位置:首页 > 运维架构 > Linux

centos6.2 64位下配置Sphinx(斯芬克司)mysql高速搜素引擎

2012-11-19 14:38 525 查看
Sphinx(斯芬克司)

Sphinx是一个基于SQL的全文检索引擎,可以结合MySQL,PostgreSQL做全文搜索,它可以提供比数据库本身更专业的搜索功能,使得应用程序更容易实现专业化的全文检索。Sphinx特别为一些脚本语言设计搜索API接口,如PHP,Python,Perl,Ruby等,同时为MySQL也设计了一个存储引擎插件。

Sphinx 单一索引最大可包含1亿条记录,在1千万条记录情况下的查询速度为0.x秒(毫秒级)。Sphinx创建索引的速度为:创建100万条记录的索引只需 3~4分钟,创建1000万条记录的索引可以在50分钟内完成,而只包含最新10万条记录的增量索引,重建一次只需几十秒。
下载安装包:

然后解压

[root@localhost src]# tar -zxf sphinx-2.0.6-release.tar.gz

[root@localhost src]# cd sphinx-2.0.6-release

[root@localhost sphinx-2.0.6-release]#./configure --prefix=/usr/local/sphinx --with-mysql=/usr/local/mysql/ --with-iconv

[root@localhost sphinx-2.0.6-release]# make && make install

#在64位系统中,后面还应该加 --enable-id64

然后,我们进入mysql把sphinx带的模板测试库导入mysql

[root@localhost sphinx-2.0.6-release]# mysql

mysql> use test

mysql> source /usr/local/sphinx/etc/example.sql;

mysql> quit

修该sphinx配置文件:

[root@localhost sphinx-2.0.6-release]# cd /usr/local/sphinx/etc/

[root@localhost etc]# cp sphinx.conf.dist sphinx.conf

[root@localhost etc]# vim sphinx.conf

sql_host = localhost

sql_user = root

sql_pass = root

sql_db = test

sql_port = 3306

然后保存退出

[root@localhost etc]# /usr/local/sphinx/bin/indexer --all

这个命令是建立索引,当然数据基础是刚刚导入的example.sql的数据,如果这里出错,最大的可能是你的sphinx.conf中的数据库配置错了,你需要回去检查并修正。但是,还有可能出现sphinx必须的库文件无法找到,例如出现以下两种错误:

/usr/local/sphinx/bin/indexer: error while loading shared libraries: libmysqlclient.so.15: cannot open shared

object file: No such file or directory

/usr/local/sphinx/bin/indexer: error while loading shared libraries: libiconv.so.2: cannot open shared object file:

No such file or directory

这主要是因为你安装了一些库后,没有能够配置相应的环境变量。你可以通过建立连接的方式修正这个问题,运行如下命令:

[root@localhost etc]# ln -s /usr/local/mysql/lib/libmysqlclient.so.15 /usr/lib/libmysqlclient.so.15

[root@localhost etc]# ln -s /usr/local/lib/libiconv.so.2 /usr/lib/libiconv.so.2

这里我假设你相应的软件包安装在/usr/local/xxx 目录下,如果你不是安装在相应目录下,你就需要使用你自己的路径。如果你没有安装libiconv软件包,则需要安装下,这个安装比较简单,就不多说了。

如果还出现类似错误,照上面的方法修正。

[root@localhost etc]# /usr/local/sphinx/bin/indexer --all --config /usr/local/sphinx/etc/sphinx.conf --rotate

[root@localhost etc]# /usr/local/sphinx/bin/search test

Sphinx 2.0.1-id64-beta (r2792)

Copyright (c) 2001-2011, Andrew Aksyonoff

Copyright (c) 2008-2011, Sphinx Technologies Inc (http://sphinxsearch.com)

using config file '/usr/local/sphinx/etc/sphinx.conf'...

index 'test1': query 'test ': returned 3 matches of 3 total in 0.015 sec

displaying matches:

1. document=1, weight=2421, group_id=1, date_added=Mon Nov 19 16:57:01 2012

id=1

group_id=1

group_id2=5

date_added=2013-01-07 14:12:18

title=test one

content=this is my test document number one. also checking search within phrases.

2. document=2, weight=2421, group_id=1, date_added=Mon Nov 19 16:57:01 2012

id=2

group_id=1

group_id2=6

date_added=2013-01-07 14:12:18

title=test two

content=this is my test document number two

3. document=4, weight=1442, group_id=2, date_added=Mon Nov 19 16:57:01 2012

id=4

group_id=2

group_id2=8

date_added=2013-01-07 14:12:18

title=doc number four

content=this is to test groups

words:

1. 'test': 3 documents, 5 hits

index 'test1stemmed': query 'test ': returned 3 matches of 3 total in 0.000 sec

displaying matches:

1. document=1, weight=2421, group_id=1, date_added=Mon Nov 19 16:57:01 2012

id=1

group_id=1

group_id2=5

date_added=2013-01-07 14:12:18

title=test one

content=this is my test document number one. also checking search within phrases.

2. document=2, weight=2421, group_id=1, date_added=Mon Nov 19 16:57:01 2012

id=2

group_id=1

group_id2=6

date_added=2013-01-07 14:12:18

title=test two

content=this is my test document number two

3. document=4, weight=1442, group_id=2, date_added=Mon Nov 19 16:57:01 2012

id=4

group_id=2

group_id2=8

date_added=2013-01-07 14:12:18

title=doc number four

content=this is to test groups

words:

1. 'test': 3 documents, 5 hits

index 'rt': search error: /usr/local/sphinx/var/data/rt.sph is invalid header file (too old index version?).

上面的命令是搜索测试,测试的关键词就是 test 了,如果成功的话,你应该看到搜到的结果,出现字串“index 'test1': query
'test ': returned 3 matches of 3 total in 0.000 sec”,后面跟的是结果表示成功了。

[root@localhost etc]# /usr/local/sphinx/bin/searchd

[root@localhost etc]# netstat -ntlp

Active Internet connections (only servers)

Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name

tcp 0 0 127.0.0.1:9000 0.0.0.0:* LISTEN 1077/php-fpm

tcp 0 0 0.0.0.0:873 0.0.0.0:* LISTEN 1416/rsync

tcp 0 0 0.0.0.0:3306 0.0.0.0:* LISTEN 1373/mysqld

tcp 0 0 0.0.0.0:80 0.0.0.0:* LISTEN 1418/nginx

tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN 1094/sshd

tcp 0 0 0.0.0.0:9306 0.0.0.0:* LISTEN 3684/searchd

tcp 0 0 0.0.0.0:9312 0.0.0.0:* LISTEN 3684/searchd

tcp 0 0 0.0.0.0:10050 0.0.0.0:* LISTEN 1427/zabbix_agentd

tcp 0 0 0.0.0.0:10051 0.0.0.0:* LISTEN 1439/zabbix_server

Sphinx.conf 配置文档参数解释

其结构组成主要如下 :

Source 源名称 1{ // 指定数据源

一些配置

}

Index 索引名称 1{

Source= 源名称 1

}

Source 源名称 2{

一些配置

}

Index 索引名称 2{

Source= 源名称 2

}

Indexer{

mem_limit = 32M

}

Searchd{ // 配置 searchd 守护程序本身

}

二. Source 源名称 相关配置说明

Type= 数据库类型 (Mysql 或 SQL);

Sql_host= 数据库主机地址 ( 如果是外网 , 请确保防火墙允许链接 )

Sql_user= 数据库用户名

Sql_pass= 数据库密码

Sql_db= 数据库名称

Sql_port= 数据库端口

Sql_query_pre= 执行 SQL 前设置的编码 (SET NAMES UTF8/GBK)

#下面的语句是更新sph_counter表中的 max_doc_id。

sql_query_pre = REPLACE INTO sph_counter SELECT 1, MAX(id) FROM document

Sql_query= 全文检索要显示的内容 , 据官方说法 : 尽可能不要使用 WHERE 或 GROUPBY , 将其交给 SPHINX 效率会更高 ;select 出来的字段必须包含至少一个唯一主键 , 以及全文检索的字段

Sql_query_info=

SELECT * FROM Inventory WHERE id=$id

Strip_html= 0/1 是否去掉 HTML 标签

Sql_attr_uint= 无符号整数属性 , 可以设置多个 , 设置数据库字段 , 设置哪个能显示出哪个字段数据的整形来 .

Sql_attr_float 浮点型

Sql_attr_timestamp 时间戳

Sql_attr_str2ordinal字符串型 这个属性类型(简称为字串序数)的设计是为了允许按字符串值排序,但不存储字符串本身。

三. Index 中配置说明

Source= 数据源名称

Path = 索引记录存放目录 , 注 : d:/sphinx/data/cg 这个的意思是 在 data 目录下创建一个名为 cg 的文件

min_word_len= 索引的词的最小长度 设为 1 既可以搜索单个字节搜索 , 越小 索引越精确 , 但建立索引花费的时间越长

charset_type= utf-8/gbk 设置数据编码

charset_table= 字符表和大小写转换规则 . 频繁应用于 sphinx 的分词过程

min_prefix_len = 最小前缀 (0)

min_infix_len = 最小中缀 (1)

//以下三句是关于UTF-8中文一元分词的配置

ngram_len = 对于非字母型数据的长度切 (1)

charset_table = 0..9, A..Z->a..z, _, a..z, U+410..U+42F->U+430..U+44F, U+430..U+44F

ngram_len = 1

ngram_chars = U+3000..U+2FA1F

四. searchd 配置说明

port= sphinx 的端口 (9312)

log= 服务进程日志存放路径,一旦 sphinx 出现异常,基本上可以从这里查询有效信息

query_log= 客户端查询日志 尤为有用 它将在运行时显示每次搜索并显示结果

read_timeout= 请求超时 (5)

max_children= 同时可执行的最大 searchd 进程数 (30)

pid_file= 进程 ID 文件

max_matches= 查询结果的最大返回数

seamless_rotate= 是否支持无缝切换,做增量索引时通常需要 (0/1)

至此 spninx.conf 配置文件结束 ; 注意 : 如果有换行 必须用反斜杠 \ 链接

五. sphinx 建立所以 及监听

切换到 DOS sphinx/bin 目录下

1. 建立索引

Indexer –c sphinx.conf 索引名称 /--all (--all 参数是建立所有索引 )

完成后提示如下 :

total 535600 docs, 10707632 bytes

total 34.323 sec, 311958 bytes/sec, 15604.27 docs/sec

total 5 reads, 0.282 sec, 45592.6 kb/call avg, 56.4 msec/call avg

total 547 writes, 12.172 sec, 1017.0 kb/call avg, 22.2 msec/call avg

2. 建立完成后

可以执行 search [–c] sphinx.conf 搜索内容 (-c 参数 : 是否允许模糊搜索 )

3. 监听端口

Searchd

运行后 提示

listening on all interfaces, port=9312

accepting connections

监听成功后 既可以运行 PHP 程序 进行 搜索

PHPCODE:

require("sphinxapi.php"); // 加载类文件

$cl=new SphinxClient(); // 实例化类

$cl->SetServer('localhost',9312); // 设置服务

$search->setSearch_start(($page -1) * $pageSize);//分页

$search->setSearch_limit($pageSize * 1);

$cl->SetArrayResult(true); // 设置 显示结果集方式

$cl->SetLimits(0,10); // 同 sql 语句中的 LIMIT

$cl->SetSortMode(“mode”); // 排序模式 SPH_SORT_ATTR_DESC 和 SPH_SORT_ATTR_ASC

$result=$cl->Query('ff',[ 索引名称可选 ]); // 执行搜索,索引名称指的是下面例子中的member, member_delta

Var_dump($result); // 输出

Sphinx.conf 配置文档案例:

source member

{

type = mysql

sql_host = localhost

sql_user = XXX

sql_pass = XXX

sql_db = XXX

sql_port = 3306

sql_query_pre = SET NAMES utf8

sql_query_pre = SET SESSION query_cache_type=OFF

sql_query = \

SELECT members.uid as uid,members.username as username FROM members where member_status =1 and uid not in \

(SELECT distinct user_id FROM `fct_faction_member` )

}

source member_delta : member

{

sql_query_pre = SET NAMES utf8

sql_query_pre = SET SESSION query_cache_type=OFF

sql_query = \

SELECT members.uid as uid,members.username as username FROM members where member_status =1 and uid not in \

(SELECT distinct user_id FROM `fct_faction_member` )

}

index member

{

source = member

path = /data0/coreseek/var/data/member_test

docinfo = extern

charset_dictpath = /usr/local/webserver/mmseg/etc/

mlock = 0

morphology = none

min_word_len = 1

html_strip = 0

charset_type = zh_cn.utf-8

ngram_len = 0

}

index member_delta

{

source = member_delta

path = /data0/coreseek/var/data/member_delta_test

docinfo = extern

charset_dictpath = /usr/local/webserver/mmseg/etc/

mlock = 0

morphology = none

min_word_len = 1

html_strip = 0

charset_type = zh_cn.utf-8

ngram_len = 0

}

sphinx的原理是每天定时的去处理一些大的sql语句,将查询出来的结果放在文件中,在你每次去搜索时是根据条件在文件的基础上去搜索的,这样节省时间!

#注意:member_delta 中的sql_query_pre的个数需和member对应,否则可能搜索不出相应的结果

例子:

source main

{

type = mysql #数据库类型

sql_host = 127.0.0.1 #数据库ip

sql_user = root #数据库用户名

sql_pass = #数据库密码

sql_db = ssc #数据库名

sql_port = 3306 # 数据库端口

sql_query_pre = SET NAMES utf8

sql_query_pre = REPLACE INTO sphinx_counter SELECT 1, MAX(searchid) FROM search_data

sql_query = SELECT searchid, adddate, siteid, typeid, contentid, data,thumb FROM search_data \

WHERE searchid>=$start AND searchid<=$end

sql_query_range = SELECT 1,max_doc_id FROM sphinx_counter WHERE counter_id=1

sql_range_step = 5000

#字符串属性设置、需要过滤、排序的时候用到

sql_attr_uint = typeid

sql_attr_uint = siteid

sql_attr_uint = contentid

sql_attr_timestamp = adddate

sql_attr_uint = thumb

sql_query_info = SELECT * FROM search_data WHERE searchid=$id

}

source delta

{

type = mysql #数据库类型

sql_host = 127.0.0.1 #数据库ip

sql_user = root #数据库用户名

sql_pass = cespc123 #数据库密码

sql_db = ssc #数据库名

sql_port = 3306 # 数据库端口

sql_query_pre = SET NAMES utf8

sql_query = SELECT searchid, adddate, siteid, typeid, contentid, data,thumb FROM search_data \

WHERE searchid >( SELECT max_doc_id FROM sphinx_counter WHERE counter_id=1 )

sql_query_post = REPLACE INTO sphinx_counter SELECT 1, MAX(searchid) FROM search_data

#字符串属性设置、需要过滤、排序的时候用到

sql_attr_uint = typeid

sql_attr_uint = siteid

sql_attr_uint = contentid

sql_attr_timestamp = adddate

sql_attr_uint = thumb

sql_query_info = SELECT * FROM search_data WHERE searchid=$id

}

#主索引

index main

{

source = main

# 放索引的目录

path = /usr/local/sphinx/var/data/ssc

# 编码

charset_type = utf-8

# 指定utf-8的编码表

charset_table = 0..9, A..Z->a..z, _, a..z, U+410..U+42F->U+430..U+44F, U+430..U+44F

# 简单分词,只支持0和1,如果要搜索中文,请指定为1

ngram_len = 1

# 需要分词的字符,如果要搜索中文,去掉前面的注释

ngram_chars = U+3000..U+2FA1F

}

#增量索引

index delta

{

source = delta

path = /usr/local/sphinx/var/data/delta

# 编码

charset_type = utf-8

# 指定utf-8的编码表

charset_table = 0..9, A..Z->a..z, _, a..z, U+410..U+42F->U+430..U+44F, U+430..U+44F

# 简单分词,只支持0和1,如果要搜索中文,请指定为1

ngram_len = 1

# 需要分词的字符,如果要搜索中文,去掉前面的注释

ngram_chars = U+3000..U+2FA1F

}

indexer

{

mem_limit = 128M

}

searchd

{

port = 9312

log = /usr/local/sphinx/var/log/searchd.log

query_log = /usr/local/sphinx/var/log/query.log

read_timeout = 5

max_children = 30

pid_file = /usr/local/sphinx/var/log/searchd.pid

max_matches = 2000

seamless_rotate = 0

preopen_indexes = 0

unlink_old = 1

compat_sphinxql_magics = 0

}

其实单纯的sphinx对中文支持不是很好,推荐使用sphinx-for-chinese
一些郁闷的错误处理

[root@localhost bin]# ./search test1 -c ../etc/sphinx.conf

sphinx-for-chinese 2.1.0-dev (r3361)

Copyright (c) 2008-2012, sphinx-search.com

using config file '../etc/sphinx.conf'...

index 'test1': search error: .

解决办法:如下标红的命令后面加参数就可以,-i是指的默认索引

[root@localhost bin]# ./search -i test1 -q 分享身边的精彩 -c ../etc/sphinx.conf

sphinx-for-chinese 2.1.0-dev (r3361)

Copyright (c) 2008-2012, sphinx-search.com

using config file '../etc/sphinx.conf'...

index 'test1': query '分享身边的精彩 ': returned 0 matches of 0 total in 0.000 sec

words:

1. '分享': 0 documents, 0 hits

2. '身边': 0 documents, 0 hits

3. '的': 0 documents, 0 hits

4. '精彩': 0 documents, 0 hits

本文出自 “杜云龙” 博客,请务必保留此出处http://duyunlong.blog.51cto.com/1054716/1063842
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: