
4.1 _search接口
_search接口可以使用GET或POST方法请求,在请求路径中可以指定一个或多个索引,还可以使用_all或者星号“*”匹配所有索引。如果不指定索引名称,实际上也是匹配所有索引。Elasticsearch为使用这个接口定义了一种查询语言——DSL(Domain Specific Language)。DSL是一套基于JSON的查询语言,这种只在某一领域使用的语言通常称为领域特定语言,而它们英文单词首字母简写就是DSL。本书后续章节都将简称这种语言为DSL,由于DSL内容非常庞杂,将在本书第5章单独介绍。
_search接口有两种请求方式,一种是基于URI的请求方式,另一种则是基于请求体的请求方式。无论是哪一种,它们执行的语法根基都是DSL,只是在使用形式上不同而已。
4.1.1 基于URI
_search接口基于URI的请求方式比较简单,DSL查询条件以请求参数q传递给接口。使用_search接口的最简形式就是不挂任何参数直接调用,可以在路径中添加索引名称,也可以不添加。所以示例4-1中的请求都是正确的:

示例4-1 基于URI的_search接口调用
在最后一个请求中,参数q定义的内容叫查询字符串(Query String),它的含义是检索message字段值中包含chrome或firefox的文档。查询字符串不仅可以在基于URI的检索中使用,也可以在基于请求体的检索中使用,是DSL定义的一种检索方法。查询字符串属于全文检索,这意味着查询字符串在检索前会被分析器解析为一系列词项和运算符。以示例4-1中的请求为例,“chrome firefox”会被解析为chrome和firefox两个词项,然后再与message字段的词项索引做匹配。只要message字段中包含chrome或firefox,这个文档就满足查询条件。
1.查询字符串
查询字符串的基本格式为“<字段名>:<查询值>”,其中字段名可以指定,也可以不指定。如果没有指定字段名,要匹配的字段由index.query.default_field参数设置。这个参数的默认值为*.*,即在所有字段中查询。此外,还可以使用参数df(Default Field)指定要查询的字段名,它与参数q一样是可以用在URI中的参数。如果指定了字段名,查询将在指定字段中匹配词项。除了直接指定字段名以外,还可使用通配符等形式匹配字段,例如:

示例4-2 特殊格式的字段名
在示例4-2中,查询字符串“geo.\ *:CN US”将在geo的子字段中匹配CN或US。第二个查询字符串中的_exists_不是一个具体的字段名,而是代表所有非空的title字段。
下面再来看看查询字符串中的查询值。查询值会在检索前通过分析器拆分为词项,在检索时只要字段中包含任意一个词项就视为满足条件。在实现上,这其实是使用了DSL语言中定义的match查询。如果使用双引号将它们括起来,_search接口将使用DSL的match_phrase做短语匹配。从效果上看就类似于用整个短语做检索,而不是使用单个词项做检索。查询值中除了包含词项本身以外,还可以包含操作符OR和AND,注意它们必须大写否则将被识别为词项。例如,“(tom smith)AND jhon”代表的含义是同时包含tom、jhon或smith、jhon的字段。除了可以包含词项、操作符以外,查询字符串的查询值中还可以包含通配符、正则表达式等。表4-1给出了一些可能的用法。
表4-1 查询字符串查询值的特殊用法

2.请求参数
基于URI调用_search接口时可以使用的参数,除了前述的q和df以外还有很多。例如,_source参数可以用来设置在返回结果中是否包含_source字段,还可以使用_source_include或_source_exclude参数包含或排除源文档的字段。这样的参数还有很多,它们大多数与基于请求体的参数具有相同的名称和含义。不仅如此,部分参数对于其他接口也可使用,所以对于参数的介绍将在本章4.2节统一讲解。表4-2先将这些参数总结出来供参考:
表4-2 基于URI的_search接口参数

4.1.2 基于请求体
基本请求体的接口调用,可以在请求体中传递DSL检索条件。尽管可以GET或POST方法请求_search接口,但由于一些客户端不支持使用GET方法发送请求体,所以最好使用POST方法请求基于请求体的_search接口。使用请求体检索时,DSL检索条件通过请求体的query参数设置。例如检索目的地为中国的航班:


示例4-3 基于请求体的检索
在示例4-3的检索中,采用了DSL基于词项(Term)的查询,检索条件是DestCountry为CN。DSL中最简单的查询关键字是match_all和match_none,它们分别代表匹配所有和都不匹配。例如:

示例4-4 match_all和match_none
除了这两种查询以外,DSL还定义了多种多样的查询语法,有关DSL的具体语法将在本书第5章做全面介绍。在请求体中可以使用的参数除了query以外还有很多,它们很多与表4-2中的URI参数名称和含义都是相同的,接下来两个小节将对一些重要的参数做介绍。