API参考

目录

Sphinx有几种不同编程语言的原生searchd客户端API的实现。在本文完成之时,我们对我们自己开发的PHP,Python和java客户端实现提供官方支持。此外,也有一些针对Perl,Ruby和C++的第三方免费、开源API实现。

API的参考实现是用PHP写成的,因为(我们相信)较之其他语言,Sphinx在PHP中应用最广泛。因此这份参考文档基于PHP API的参考,而且这节中的所有的代码样例都用PHP给出。

当然,其他所有API都提供相同的方法,也使用完全相同的网络协议。因此这份文档对他们同样适用。在方法命名习惯方面或者具体数据结构的使用上可能会有小的差别。但不同语言的API提供的功能上绝不会有差异。

8.1. 通用API方法

8.1.1. GetLastError (错误信息)

原型: function GetLastError()

以可读形式返回最近的错误描述信息。如果前一次API调用没有错误,返回空字符串。

任何其他函数(如 Query())失败后(函数失败一般返回false),都应该调用这个函数,它将返回错误的描述。

此函数本身并重置对错误描述,因此如有必要,可以多次调用。

8.1.2. GetLastWarning (告警信息)

原型: function GetLastWarning ()

以可读格式返回最近的警告描述信息。如果前一次API调用没有警告,返回空字符串。

您应该调用这个函数来确认您的请求(如 Query())是否虽然完成了但产生了警告。例如,即使几个远程代理超时了,对分布式索引的搜索查询也可能成功完成。这时会产生一个警告信息。

此函数本身会重置警告信息,因此如有必要,可以多次调用。

8.1.3. SetServer (设置搜索服务)

原型: function SetServer ( $host, $port )

设置searchd的主机名和TCP端口。此后的所有请求都使用新的主机和端口设置。默认的主机和端口分别是“localhost”和9312。

8.1.4. SetRetries (设置失败重试)

原型: function SetRetries ( $count, $delay=0 )

设置分布式搜索重试的次数和延迟时间。

对于暂时的失败,searchd对每个代理重试至多$count次。$delay是两次重试之间延迟的时间,以毫秒为单位。默认情况下,重试是禁止的。注意,这个调用不会使API本身对暂时失败进行重试,它只是让searchd这样做。目前暂时失败包括connect()调用的各种失败和远程代理超过最大连接数(过于繁忙)的情况。

8.1.5. SetConnectTimeout (设置超时时间)

原型: function SetConnectTimeout ( $timeout )

设置连接超时时间,在与服务器连接时,如果超过这个时间没有连上就放弃。

有时候服务器在响应上会有所延迟,这有可能由于网络的延时,也有可能是因为服务器未处理完的查询太多,堆积所致。不管是什么情况,有了这个选项,就给客户端应用程序提供了一定的控制权,让它可以决定当searchd不可用的时候如何处理,而且可以避免脚本由于超过运行限制而运行失败(尤其是在PHP里)

当连接失败的而时候,会将合适的错误码返回给应用程序,以便在应用程序级别进行错误处理和通知用户。

8.1.6. SetArrayResult (设置结果返回格式)

原型: function SetArrayResult ( $arrayresult )

PHP专用。控制搜索结果集的返回格式(匹配项按数组返回还是按hash返回)

$arrayresult 参数应为布尔型。如果$arrayresultfalse(默认),匹配项以PHP hash格式返回,文档ID为键,其他信息(权重、属性)为值。如果$arrayresulttrue,匹配项以普通数组返回,包括匹配项的全部信息(包含文档ID)。

这个调用是对MVA属性引入分组支持时同时引入的。对MVA分组的结果可能包含重复的文档ID。因此需要将他们按普通数组返回,因为hash对每个文档ID仅能保存一个记录。

8.1.7. IsConnectError (检查链接错误)

原型: function IsConnectError ()

检查上一个错误是API层面的网络错误还是searchd返回的远程错误。如果是上一次连接searchd的尝试在API层面失败了,返回真,否则返回假(错误发生在远程,或者根本没有尝试连接)。 这是在版本0.9.9-rc1引入的。

8.2. 通用搜索设置

8.2.1. SetLimits (设置结果集偏移量)

原型: function SetLimits ( $offset, $limit, $max_matches=0, $cutoff=0 )

给服务器端结果集设置一个偏移量($offset)和从那个偏移量起向客户端返回的匹配项数目限制($limit)。并且可以在服务器端设定当前查询的结果集大小($max_matches),另有一个阈值($cutoff),当找到的匹配项达到这个阀值时就停止搜索。全部这些参数都必须是非负整数。

前两个参数的行为与MySQL LIMIT子句中参数的行为相同。他们令searchd从编号为$offset的匹配项开始返回最多$limit个匹配项。偏移量($offset)和结果数限制($limit)的默认值分别是0和20,即返回前20个匹配项。

max_matches这个设置控制搜索过程中searchd在内存中所保持的匹配项数目。一般来说,即使设置了max_matches为1,全部的匹配文档也都会被处理、评分、过滤和排序。但是任一时刻只有最优的N个文档会被存储在内存中,这是为了性能和内存使用方面的原因,这个设置正是控制这个N的大小。注意,max_matches两个地方设置。针对单个查询的限制由这个API调用指定。但还有一个针对整个服务器的限制,那是由配置文件中的max_matches设置控制的。为防止滥用内存,服务器不允许单个查询的限制高于服务器的限制。

在客户端不可能收到超过max_matches个匹配项。默认的限制是1000,您应该不会遇到需要设置得更高的情况。1000个记录足够向最终用户展示了。如果您是想将结果传输给应用程序以便做进一步排序或过滤,那么请注意,在Sphinx端完成效率要得多。

$cutoff设置是为高级性能优化而提供的。它告诉searchd 在找到并处理$cutoff个匹配后就强制停止。

8.2.2. SetMaxQueryTime (设置最大搜索时间)

原型: function SetMaxQueryTime ( $max_query_time )

设置最大搜索时间,以毫秒为单位。参数必须是非负整数。默认值为0,意思是不做限制。

这个设置与SetLimits()中的$cutoff相似,不过这个设置限制的是查询时间,而不是处理的匹配数目。一旦处理时间已经太久,本地搜索查询会被停止。注意,如果一个搜索查询了多个本地索引,那这个限制独立地作用于这几个索引。

8.2.3. SetOverride (设置临时属性值覆盖)

原型: function SetOverride ( $attrname, $attrtype, $values )

设置一个临时的(只对单个查询有效)针对不同文档的属性值覆盖。只支持标量属性。$value是一个哈希表,他的键是要覆盖属性的文档ID,之是对应该文档ID的要覆盖的值。 于版本0.9.9-rc1引入。

属性覆盖特性使用户可以针对一次查询“临时性地”修改一些文档的值,不影响其他查询。这个函数可以用来进行数据个性化。例如,假设正在实现一个个性化搜索 函数,用来将朋友推荐的帖子排在前面,这类数据不仅是动态的,而且是个性化的,因此不能简单地把这种数据放入索引,因为不能影响其他用户的搜索。而覆盖机 制是针对单个查询的,不会影响其他人。因此可以,比如说,给每个文档设置一个“friends_weight”属性,默认值是0,然后临时将文档 123,456,789(当前用户的朋友推荐的)的这个属性设置为1,最后用这个值进行相关度计算。

8.2.4. SetSelect (设置返回信息的内容)

原型: function SetSelect ( $clause )

设置select子句,列出具体要取出的属性以及要计算并取出的expressions。子句的语法模仿了SQL。于版本0.9.9-rc1引入。

SetSelect()于标准SQL查询中SELECT和FROM之间的部分非常相近。它允许你指定要取出哪些属性(列),以及在这些列上要计算和取出哪 些表达式。与SQL语言的区别是,表达式必须用关键字AS给每个表达式取一个别名,别名必须是有效的标识符(由字母和数字组成)。在SQL里面可以这样 做,但是不是强制的。Sphinx强制必须有别名,以便计算结果总是可以以一个“正常”的名字在结果集中返回,或者在其他子句中引用,等等。

其他方面基本上等同于SQL。支持星号(“*”),支持函数,支持任意数目的表达式。计算出的表达式可以用于排序、过滤和分组,这与其他常规属性相同。

从版本0.9.9-rc2开始,允许使用GROUP BY的时候使用聚集函数(AVG(), MIN(), MAX(), SUM())。

表达式排序(第 5.6 节 “SPH_SORT_EXPR 模式”)和地理距离计算函数(第 8.4.5 节 “SetGeoAnchor (设置地表距离锚点)”)现在的内部实现就是这种表达式计算机制,分别使用“魔法名字”“@expr”和“@geodist”。

示例:

$cl->SetSelect ( "*, @weight+(user_karma+ln(pageviews))*0.1 AS myweight" );
$cl->SetSelect ( "exp_years, salary_gbp*{$gbp_usd_rate} AS salary_usd,
   IF(age>40,1,0) AS over40" );
$cl->SetSelect ( "*, AVG(price) AS avgprice" );

8.3. 全文搜索设置

8.3.1. SetMatchMode (设置匹配模式)

原型: function SetMatchMode ( $mode )

设置全文查询的匹配模式,见第 5.1 节 “匹配模式”中的描述。参数必须是一个与某个已知模式对应的常数。

警告: (仅PHP)查询模式常量不能包含在引号中,那给出的是一个字符串而不是一个常量:

$cl->SetMatchMode ( "SPH_MATCH_ANY" ); // INCORRECT! will not work as expected
$cl->SetMatchMode ( SPH_MATCH_ANY ); // correct, works OK

8.3.2. SetRankingMode (设置评分模式)

原型: function SetRankingMode ( $ranker )

设置评分模式。目前只在SPH_MATCH_EXTENDED2这个匹配模式中提供。参数必须是与某个已知模式对应的常数。

Sphinx默认计算两个对最终匹配权重有用的因子。主要是查询词组与文档文本的相似度。其次是称之为BM25的统计函数,该函数值根据关键字文档中的频率(高频导致高权重)和在整个索引中的频率(低频导致高权重)在0和1之间取值。

然而,有时可能需要换一种计算权重的方法——或者可能为了提高性能而根本不计算权值,结果集用其他办法排序。这个目的可以通过设置合适的相关度计算模式来达到。

已经实现的模式包括:

  • SPH_RANK_PROXIMITY_BM25, 默认模式,同时使用词组评分和BM25评分,并且将二者结合。

  • SPH_RANK_BM25, 统计相关度计算模式,仅使用BM25评分计算(与大多数全文检索引擎相同)。这个模式比较快,但是可能使包含多个词的查询的结果质量下降。

  • SPH_RANK_NONE, 禁用评分的模式,这是最快的模式。实际上这种模式与布尔搜索相同。所有的匹配项都被赋予权重1。

  • SPH_RANK_WORDCOUNT, 根据关键词出现次数排序。这个排序器计算每个字段中关键字的出现次数,然后把计数与字段的权重相乘,最后将积求和,作为最终结果。

  • SPH_RANK_PROXIMITY, 版本0.9.9-rc1新增,将原始的词组相似度作为结果返回。在内部,这个模式被用来模拟SPH_MATCH_ALL的查询。

  • SPH_RANK_MATCHANY, 版本0.9.9-rc1新增,返回之前在SPH_MATCH_ANY中计算的位次,在内部这个模式用于模拟SPH_MATCH_ANY的查询。

  • SPH_RANK_FIELDMASK, 版本0.9.9-rc2新增,返回一个32位掩码,其中第N位对应第N个全文字段,从0开始计数,如果某个字段中出现了满足查询的关键词,则对应的标志位被置1。

  • SPH_RANK_SPH04, 版本1.10-beta新增, 基本功能给予默认的 SPH_RANK_PROXIMITY_BM25 评分, 但是当他们在一段文本的最开始或者最后匹配时作了进一步处理。也就是说,当一个字段严格匹配查询时,相对于一个包含查询而非完全相同的字段,SPH04会 给予更高的评分。(例如,当查询为"Hyde Park"时,一篇名称为"Hyde Park"的文档取得的评分将高于一篇名称为 "Hyde Park, London" 或者 "The Hyde Park Cafe"的文档。)

8.3.3. SetSortMode (设置排序模式)

原型: function SetSortMode ( $mode, $sortby="" )

设置匹配项的排序模式,见第 5.6 节 “排序模式”中的描述。参数必须为与某个已知模式对应的常数。

警告: (仅PHP)查询模式常量不能包含在引号中,那给出的是一个字符串而不是一个常量:

$cl->SetSortMode ( "SPH_SORT_ATTR_DESC" ); // INCORRECT! will not work as expected
$cl->SetSortMode ( SPH_SORT_ATTR_ASC ); // correct, works OK

8.3.4. SetWeights (设置权重)

原型: function SetWeights ( $weights )

按在索引中出现的先后顺序给字段设置权重。 不推荐使用, 建议使用 SetFieldWeights()

8.3.5. SetFieldWeights (设置字段权重)

原型: function SetFieldWeights ( $weights )

按字段名称设置字段的权值。参数必须是一个hash(关联数组),该hash将代表字段名字的字符串映射到一个整型的权值上。

字段权重影响匹配项的评级。第 5.4 节 “权值计算” 解释了词组相似度如何影响评级。这个调用用于给不同的全文数据字段指定不同于默认值的权值。

给定的权重必须是正的32位整数。最终的权重也是个32位的整数。默认权重为1。未知的属性名会被忽略。

目前对权重没有强制的最大限制。但您要清楚,设定过高的权值可能会导致出现32位整数的溢出问题。例如,如果设定权值为10000000并在扩展模式中进行搜索,那么最大可能的权值为10M(您设的值)乘以1000(BM25的内部比例系数,参见第 5.4 节 “权值计算”, “权值计算”)再乘以1或更多(词组相似度评级)。上述结果最少是100亿,这在32位整数里面没法存储,将导致意想不到的结果。

8.3.6. SetIndexWeights (设置索引权重)

原型: function SetIndexWeights ( $weights )

设置索引的权重,并启用不同索引中匹配结果权重的加权和。参数必须为在代表索引名的字符串与整型权值之间建立映射关系的hash(关联数组)。默认值是空数组,意思是关闭带权加和。

当在不同的本地索引中都匹配到相同的文档ID时,Sphinx默认选择查询中指定的最后一个索引。这是为了支持部分重叠的分区索引。

然而在某些情况下索引并不仅仅是被分区了,您可能想将不同索引中的权值加在一起,而不是简单地选择其中的一个。SetIndexWeights()允许您这么做。当开启了加和功能后,最后的匹配权值是各个索引中的权值的加权合,各索引的权由本调用指定。也就是说,如果文档123在索引A被找到,权值是2,在B中也可找到,权值是3,而且您调用了SetIndexWeights ( array ( "A"=>100, "B"=>10 ) ),那么文档123最终返回给客户端的权值为2*100+3*10 = 230。

8.4. 结果集过滤设置

8.4.1. SetIDRange (设置查询ID范围)

原型: function SetIDRange ( $min, $max )

设置接受的文档ID范围。参数必须是整数。默认是0和0,意思是不限制范围。

此调用执行后,只有ID在$min$max(包括$min$max)之间的文档会被匹配。

8.4.2. SetFilter (设置属性过滤)

原型: function SetFilter ( $attribute, $values, $exclude=false )

增加整数值过滤器。

此调用在已有的过滤器列表中添加新的过滤器。$attribute是属性名。$values是整数数组。$exclude是布尔值,它控制是接受匹配的文档(默认模式,即$exclude为false时)还是拒绝它们。

只有当索引中$attribute列的值与$values中的任一值匹配时文档才会被匹配(或者拒绝,如果$exclude值为true)

8.4.3. SetFilterRange (设置属性范围)

原型: function SetFilterRange ( $attribute, $min, $max, $exclude=false )

添加新的整数范围过滤器。

此调用在已有的过滤器列表中添加新的过滤器。$attribute是属性名, $min $max定义了一个整数闭区间,$exclude布尔值,它控制是接受匹配的文档(默认模式,即$exclude为false时)还是拒绝它们。

只有当索引中$attribute列的值落在$min  $max之间(包括$min  $max),文档才会被匹配(或者拒绝,如果$exclude值为true)。

8.4.4. SetFilterFloatRange (设置浮点数范围)

原型: function SetFilterFloatRange ( $attribute, $min, $max, $exclude=false )

增加新的浮点数范围过滤器。

此调用在已有的过滤器列表中添加新的过滤器。$attribute是属性名, $min $max定义了一个浮点数闭区间,$exclude必须是布尔值,它控制是接受匹配的文档(默认模式,即$exclude为false时)还是拒绝它们。

只有当索引中$attribute列的值落在$min  $max之间(包括$min  $max),文档才会被匹配(或者拒绝,如果$exclude值为true)。

8.4.5. SetGeoAnchor (设置地表距离锚点)

原型: function SetGeoAnchor ( $attrlat, $attrlong, $lat, $long )

为地理距离计算设置锚点,并且允许使用它们。

$attrlat  $attrlong是字符串,分别指定了对应经度和纬度的属性名称。$lat  $long是浮点值,指定了锚点的经度和纬度值,以角度为单位。

一旦设置了锚点,您就可以在您的过滤器和/或排序表达式中使用"@geodist"特殊属性。Sphinx将在每一次全文检索中计算给定经纬度与锚点之前的地表距离,并把此距离附加到匹配结果上去。SetGeoAnchor和索引属性数据中的经纬度值都是角度。而结果会以米为单位返回,因此地表距离1000.0代表1千米。一英里大约是1609.344米。

8.5. 分组设置

8.5.1. SetGroupBy (设置分组的属性)

原型: function SetGroupBy ( $attribute, $func, $groupsort="@group desc" )

设置进行分组的属性、函数和组间排序模式,并启用分组(参考第 5.7 节 “结果分组(聚类)”中的描述)。

$attribute是字符串,为进行分组的属性名。$func为常数,它指定内建函数,该函数以前面所述的分组属性的值为输入,目前的可选的值为: SPH_GROUPBY_DAY、SPH_GROUPBY_WEEK、 SPH_GROUPBY_MONTH、 SPH_GROUPBY_YEAR、SPH_GROUPBY_ATTR 。 $groupsort 是控制分组如何排序的子句。其语法与第 5.6 节 “SPH_SORT_EXTENDED mode”中描述的相似。

分组与SQL中的GROUP BY子句本质上相同。此函数调用产生的结果与下面伪代码产生的结果相同。

SELECT ... GROUP BY $func($attribute) ORDER BY $groupsort

注意,影响最终结果集中匹配项顺序的是$groupsort。排序模式(见第 8.3.3 节 “SetSortMode (设置排序模式)”)影响每个分组的顺序,即每组内哪些匹配项被视为最佳匹配。比如,组之间可以根据每组中的匹配项数量排序的同时每组组内又根据相关度排序。

从版本 0.9.9-rc2 开始, 聚合函数 (AVG(), MIN(), MAX(), SUM()) 可以在GROUP BY时被 SetSelect() API 调用。

从版本2.0.1-beta开始, 支持按照字符串属性分组(根据其当前字符集校对)。

8.5.2. SetGroupDistinct (设置分组计算不同值的属性)

原型: function SetGroupDistinct ( $attribute )

设置分组中需要计算不同取值数目的属性名。只在分组查询中有效。

$attribute是包含属性名的字符串。每个组的这个属性的取值都会被储存起来(只要内存允许),其后此属性在此组中不同值的总数会被计算出来并返回给客户端。这个特性与标准SQL中的COUNT(DISTINCT)子句类似。因此如下Sphinx调用

$cl->SetGroupBy ( "category", SPH_GROUPBY_ATTR, "@count desc" );
$cl->SetGroupDistinct ( "vendor" );

等价于如下的SQL语句:

SELECT id, weight, all-attributes,
	COUNT(DISTINCT vendor) AS @distinct,
	COUNT(*) AS @count
FROM products
GROUP BY category
ORDER BY @count DESC

在上述示例伪代码中,SetGroupDistinct()调用只与COUNT(DISINCT vendor)对应。GROUP BYORDER ByCOUNT(*)子句则与SetGroupBY()调用等价。两个查询都会在每类中返回一个匹配的行。除了索引中的属性,匹配项还可以包含每类的匹配项计数和每类中不同来源 ID的计数。

8.6. 搜索数据

8.6.1. Query (查询)

原型: function Query ( $query, $index="*", $comment="" )

连接到searchd服务器,根据服务器的当前设置执行给定的查询,取得并返回结果集。

$query是查询字串,$index是包含一个或多个索引名的字符串。一旦发生一般错误,则返回假并设置GetLastError()信息。若成功则返回搜索的结果集。 此外, $comment 将被发送到查询日志中搜索部分的前面,这对于调试是非常有用的。目前,注释的长度限制为128个字符以内。

$index的默认值是"*",意思是对全部本地索引做查询。索引名中允许的字符包括拉丁字母(a-z),数字(0-9),减号(-)和下划线(_),其他字符均视为分隔符。因此,下面的示例调用都是有效的,而且会搜索相同的两个索引:

$cl->Query ( "test query", "main delta" );
$cl->Query ( "test query", "main;delta" );
$cl->Query ( "test query", "main, delta" );

给出多个索引时索引的顺序是有意义的。如果同一个文档ID的文档在多个索引中找到,那么权值和属性值会取最后一个索引中所存储的作为该文档ID的权值和属性值,用于排序、过滤,并返回给客户端(除非用SetIndexWeights()显式改变默认行为)。因此在上述示例中,索引“delta”中的匹配项总是比索引“main”中的更优先。

如果搜索成功,Query()返回的结果集包含找到的全部匹配项中的一部分(根据SetLimits()之设定)和与查询相关的统计数据。结果集是hash(仅PHP,其他语言的API可能使用其他数据结构) ,包含如下键和值:

  • "matches":

  • 是一个hash表,存储文档ID以及其对应的另一个包含文档权重和属性值的hash表(或者,如果启用了SetArrayResult()则返回数组)。

  • "total":

  • 本查询在搜索服务器检索所得的匹配文档总数(即服务器端结果集的大小)。这是在当前设置下,用当前查询可以从服务器端获得的搜索结果(匹配文档)数目的上限。其最大限制值由SetLimits()设定。

  • "total_found":

  • (搜索服务器上找到和处理了的)索引中匹配文档的总数。其与total的差别在于:total表示客户端实际可以读取的结果数目,而total_found仅表示服务器端存在多少匹配的文档(永远不会比total小)。

  • "words":

  • hash表,它将查询关键字(关键字已经过大小写转换,取词干和其他处理)映射到一个包含关于关键字的统计数据(“docs”——在多少文档中出现,“hits”——共出现了多少次)的小hash表上。

  • "error":

  • searchd 报告的错误信息(人性化可读的字符串)。若无错误则为空字符串。

  • "warning":

  • searchd报告的警告信息(人类可读字符串)。若无警告则为空串。

需要指出的是 Query() 索执行的操作,与没有中间步骤的 AddQuery() RunQueries() 相同 ; 它类似一次单独的AddQuery()调用,紧跟一次相应的RunQueries()调用,然后返回匹配的第一个数组元素 (从第一次,也是仅有的一次查询返回)。

8.6.2. AddQuery (增加批量查询)

原型: function AddQuery ( $query, $index="*", $comment="" )

向批量查询增加一个查询。$query为查询串。$index为包含一个或多个索引名的字符串。 此外, 如果提供了$comment,它 将被发送到查询日志中搜索部分的前面,这对于调试是非常有用的。目前,注释的长度限制为128个字符以内。返回RunQueries()返回的数组中的一个下标。

批量查询(或多查询)使searchd能够进行可能的内部优化,并且无论在任何情况下都会减少网络连接和进程创建方面的开销。相对于单独的查询,批量查询不会引入任何额外的开销。因此当您的Web页运行几个不同的查询时,一定要考虑使用批量查询。

例如,多次运行同一个全文查询,但使用不同的排序或分组设置,这会使searchd仅运行一次开销昂贵的全文检索和相关度计算,然后在此基础上产生多个分组结果。

有时您不仅需要简单地显示搜索结果,而且要显示一些与类别相关的计数信息,例如按制造商分组后的产品数目,此时批量查询会节约大量的开销。若无批量查询, 您会必须将这些本质上几乎相同的查询运行多次并取回相同的匹配项,最后产生不同的结果集。若使用批量查询,您只须将这些查询简单地组成一个批量查 询,Sphinx会在内部优化掉这些冗余的全文搜索。

AddQuery()在内部存储全部当前设置状态以及查询,您也可在后续的AddQuery()调用中改变设置。早先加入的查询不会被影响,实际上没有任何办法可以改变它们。下面是一个示例:

$cl->SetSortMode ( SPH_SORT_RELEVANCE );
$cl->AddQuery ( "hello world", "documents" );

$cl->SetSortMode ( SPH_SORT_ATTR_DESC, "price" );
$cl->AddQuery ( "ipod", "products" );

$cl->AddQuery ( "harry potter", "books" );

$results = $cl->RunQueries ();

用上述代码,第一个查询会在“documents”索引上查询“hello world”并将结果按相关度排序,第二个查询会在“products”索引上查询“ipod”并将结果按价格排序,第三个查询在“books”索引上搜 索“harry potter”,结果仍按价格排序。注意,第二个SetSortMode()调用并不会影响第一个查询(因为它已经被添加了),但后面的两个查询都会受影响。

此外,在AddQuery()之前设置的任何过滤,都会被后续查询继续使用。因此,如果在第一个查询前使用SetFilter(),则通过AddQuery()执行的第二个查询(以及随后的批量查询)都会应用同样的过滤,除非你先调用ResetFilters()来清除过滤规则。同时,你还可以随时加入新的过滤规则

AddQuery()并不修改当前状态。也就是说,已有的全部排序、过滤和分组设置都不会因这个调用而发生改变,因此后续的查询很容易地复用现有设置。

AddQuery()返回RunQueries()结果返回的数组中的一个下标。它是一个从0开始的递增整数,即,第一次调用返回0,第二次返回1,以此类推。这个方便的特性使你在需要这些下标的时候不用手工记录它们。

8.6.3. RunQueries (执行批量查询)

原型: function RunQueries ()

连接到searchd,运行由AddQuery()添加的全部查询,获取并返回它们的结果集。若发生一般错误(例如网络I/O失败)则返回假并设置GetLastError()信息。若成功则返回结果集的简单数组。

该数组中的每一个结果集都跟Query()返回的结果集完全相同。

注意,批量查询请求自身几乎总是成功——除非有网络错误、正在进行索引轮换,或者其他导致整个查询无法被处理的因素。

然而其中的单个的查询很可能失败。此时与之对应的结果集只包含一个非空的"error"信息,而没有关于匹配或查询的统计信息。在极端情况下,批量查询中的所有单个查询可能都失败。但这仍然不会导致报告一般错误,因为API已经成功地连接到searchd,提交了批量查询并得到返回结果——但每个结果集都只包含特定的错误信息。

8.6.4. ResetFilters (清除当前设置的过滤器)

原型: function ResetFilters ()

清除当前设置的过滤器。

通常此调用在使用批量查询的时候会用到。您可能需要为批量查询中的不同查询提供不同的过滤器,为达到这个目的,您需要调用ResetFilters()然后用其他调用增加新的过滤器。

8.6.5. ResetGroupBy (清除现有的分组设置)

原型: function ResetGroupBy ()

清除现有的全部分组设置,并取消分组设定。

通常此调用在使用批量查询的时候会用到。单独的分组设置可以用SetGroupBy()SetGroupDistinct()来改变,但它们不能关闭分组。ResetGroupBy()将之前的分组设置彻底重置并在当前状态下关闭分组模式,因此后续的AddQuery()可以进行无分组的搜索。

8.7. 附加方法

8.7.1. BuildExcerpts (产生文本摘要和高亮)

原型: function BuildExcerpts ( $docs, $index, $words, $opts=array() )

该函数用来产生文档片段(摘要)。连接到searchd,要求它从指定文档中产生片段(摘要),并返回结果。

$docs为包含各文档内容的数组。$index为包含索引名字的字符串。给定索引的不同设置(例如字符集、形态学、词形等方面的设置)会被使用。$words为包含需要高亮的关键字的字符串。它们会按索引的设置被处理。例如,如果英语取词干(stemming)在索引中被设置为允许,那么即使关键词是“shoe”,“shoes”这个词也会被高亮。从版本0.9.9-rc1开始,关键字可以包含通配符,与查询支持的star-syntax类似。$opts为包含其他可选的高亮参数的hash表:

  • "before_match":

  • 在匹配的关键字前面插入的字符串。从版本 1.10-beta开始,可以在该字符串中使用%PASSAGE_ID%宏。该宏会被替换为当前片段的递增值。递增值的起始值默认为1,但是可以通 过"start_passage_id"设置覆盖。在多文档中调用时,%PASSAGE_ID%会在每篇文档中重新开始。默认为"<b>"。

  • "after_match":

  • 在匹配的关键字后面插入的字符串。从版本1.10-beta开始,可以在该字符串中使用%PASSAGE_ID%宏。默认为 "</b>"。

  • "chunk_separator":

  • 在摘要块(段落)之间插入的字符串。默认为" ... ".

  • "limit":

  • 摘要最多包含的符号(码点)数。整数,默认为256。

  • "around":

  • 每个关键词块左右选取的词的数目。整数,默认为 5.

  • "exact_phrase":

  • 是否仅高亮精确匹配的整个查询词组,而不是单独的关键词。布尔值,默认为false.

  • "single_passage":

  • 是否仅抽取最佳的一个区块。布尔值,默认为false.

  • "use_boundaries":

  • 是否跨越由phrase_boundary选项设置的词组边界符。布尔型,默认为false.

  • "weight_order":

  • 对于抽取出的段落,要么根据相关度排序(权重下降),要么根据出现在文档中的顺序(位置递增)。布尔型,默认是false.

  • "query_mode":

  • 版本1.10-beta新增。设置将$words当作 扩展查询语法的 查询处理,还是当做普通的文本字符串处理(默认行为)。例如,在查询模式时,("one two" | "three four")仅高亮和包含每个片段中出现"one two" 或 "three four" 的地方及相邻的部分。而在默认模式时, 每个单独出现"one", "two", "three", 或 "four"的地方都会高亮。布尔型,默认是false。

  • "force_all_words":

  • 版本1.10-beta新增. 忽略摘要的长度限制直至包含所有的词汇。布尔型,默认为false.

  • "limit_passages":

  • 版本1.10-beta新增. 限制摘要中可以包含的最大区块数。整数值,默认为 0 (不限制).

  • "limit_words":

  • 版本1.10-beta新增. 限制摘要中可以包含的最大词汇数。整数值,默认为 0 (不限制).

  • "start_passage_id":

  • 版本1.10-beta新增. 设置 %PASSAGE_ID% 宏的起始值 (在before_match, after_match 字符串中检查和应用). 整数值,默认为1.

  • "load_files":

  • 版本1.10-beta新增. 设置是否将$docs作为摘要抽取来源的数据(默认行为),或者将其当做文件名。从版本2.0.1-beta开始,如果该标志启用,每个请求将创建最多dist_threads个工作线程进行并发处理。布尔型,默认为false.

  • "html_strip_mode":

  • 版本1.10-beta新增. HTML标签剥离模式设置。默认为"index",表示使用index的设置。可以使用的其他值为"none"和"strip",用于强制跳过或者应用剥 离,而不管索引如何设置的。还可以使用"retain",表示保留HTMK标签并防止高亮时打断标签。"retain"模式仅用于需要高亮整篇文档,并且 不能设置限制片段的大小。字符型,可用值为"none","strip","index"或者"retain"。

  • "allow_empty":

  • 版本1.10-beta新增. 允许无法产生摘要时将空字符串作为高亮结果返回 (没有关键字匹配或者不符合片段限制。). 默认情况下,原始文本的开头会被返回而不是空字符串。布尔型,默认为false.

  • "passage_boundary":

  • 版本2.0.1-beta新增. 确保区块不跨越句子,段落或者zone区域(仅当每个索引的设置启用时有效)。字符型,可用值为 "sentence", "paragraph", 或者 "zone".

  • "emit_zones":

  • 版本2.0.1-beta新增. 在每个区块前使用区域对应的HTML标签来封闭区域。布尔型,魔默认为false。

摘要提取算法倾向于提取更好的片段(与关键词完全匹配),然后是不在摘要中但是包含了关键词的片段。 通常情况下,它会尝试高亮查询的最佳匹配,并且在限制条件下尽可能的高亮查询中的所有关键词。 如果文档没有匹配查询,默认情况下将根据限制条件返回文档的头部。从版本1.10-beta开始,可以通过设置allow_empty属性位true以返回空的片段来替代默认方式。

失败时返回false。成功时返回包含有片段(摘要)字符串的数组。

8.7.2. UpdateAttributes (更新属性)

原型: function UpdateAttributes ( $index, $attrs, $values )

立即更新指定文档的指定属性值。成功则返回实际被更新的文档数目(0或更多),失败则返回-1。

$index 为待更新的(一个或多个)索引名。$attrs为属性名字符串的数组,其所列的属性会被更新。$attrs为hash表,$values表的键为文档ID,$values表的值为新的属性值的简单数组。

$index 既可以是一个单独的索引名,也可以是一个索引名的列表,就像Query()的参数。与Query()不同的是不允许通配符,全部待更新的索引必须明确指出。索引名列表可以包含分布式索引。对分布式索引,更新会同步到全部代理上。

只有在docinfo=extern这个存储策略下才可以运行更新。更新非常快,因为操作完全在内存中进行,但它们也可以变成持久的,更新会在searchd干净关闭时(收到SIGTERM信号时)被写入磁盘。在额外限制条件下,MVA属性也可以被更新,参见mva_updates_pool详细了解。

使用示例:

$cl->UpdateAttributes ( "test1", array("group_id"), array(1=>array(456)) );
$cl->UpdateAttributes ( "products", array ( "price", "amount_in_stock" ),
	array ( 1001=>array(123,5), 1002=>array(37,11), 1003=>(25,129) ) );

第一条示例语句会更新索引“test1”中的文档1,设置“group_id”为456.第二条示例语句则更新索引“products”中的文档 1001,1002和1003。文档1001的“price”会被更新为123,“amount_in_stock”会被更新为5;文档 1002,“price”变为37而“amount_in_storage”变为11,等等。

8.7.3. BuildKeywords (获取分词结果)

原型: function BuildKeywords ( $query, $index, $hits )

根据指定索引的符号化(tokenizer)方式的设置,从查询中抽取关键词,也可以同时返回每个关键词出现次数的统计信息。返回一个数组,其元素是一些字典,每个字典包含一个关键字的信息。

$query 是抽取关键字的目标。$index是某个索引的名字,系统会使用这个索引的符号化(tokenizer)设置,关键词出现次数的统计信息也从这个索引中得出。$hits是一个布尔值,它指定了是否需要返回关键词出现此处的信息。

使用示例:

$keywords = $cl->BuildKeywords ( "this.is.my query", "test1", false );

8.7.4. EscapeString (转义特殊字符)

原型: function EscapeString ( $string )

查询语言分析器将某些字符理解成特殊操作符,这个函数对字符串中的那些有特殊意义的字符进行转义。返回转义后的字符串。

$string 是待转义的字符串。

表面上看这个函数是多余的,因为可以很容易地在可能调用这个函数的程序里实现这个转义功能。然而这些特殊字符的集合可能随着时间而改变,因此理应提供一个API调用来完成这个功能,并保证任何时候都可以正确地转义全部特殊字符。

使用示例:

$escaped = $cl->EscapeString ( "escaping-sample@query/string" );

8.7.5. Status (查询服务状态)

原型: function Status ()

查询searchd的状态,返回一个数组,数组元素是由状态变量名和值的键值对构成。

使用示例:

$status = $cl->Status ();
foreach ( $status as $row )
	print join ( ": ", $row ) . "\n";

8.7.6. FlushAttributes (强制更新属性到磁盘)

原型: function FlushAttributes ()

强制 searchd 刷新等待更新的属性到磁盘,并阻塞访问直到完成。 成功时返回一个非负的内部刷新标记值。错误时返回-1,并设置错误信息。 版本2.0.1-beta引入。

使用UpdateAttributes()API调用更新的属性值将一直保存在内存中,直到一次这样的刷新(将当前所有可能需要更新的属性值写回到磁盘)。FlushAttributes()调用将强制执行一次更新。 调用后将会阻塞访问直到searchd将数据全部写入到磁盘,这个过程可能会需要数秒或者数分钟,这取决于所有待更新数据的大小(.spa文件的大小)。所有当前被更新的索引都会被刷新。

刷新标记仅仅是一个不断增长的不定数值,并没有实际意义。它一定是一个非负值,并且随着时间而增长,但是并不一定是连续增长;例如,两个调用分别返回10 和1000,他们都是有效的返回值。如果两个FlushAttributes()调用返回相同的标记值,就意味着没有在他们两者之间任何实际的属性更新, 英雌当前的刷新状态将保持不变(所有索引)。

使用示例:

$status = $cl->FlushAttributes ();
if ( $status<0 )
	print "ERROR: " . $cl->GetLastError();

8.8. 持久连接

“持久连接”特性允许利用一个单独的网络连接来运行本来需要多个连接的多个命令。

8.8.1. Open (打开连接)

原型: function Open ()

打开到服务器的持久连接。

8.8.2. Close (关闭连接)

原型: function Close ()

关闭先前打开的持久连接。