我在Elasticsearch中有一些类似的数据:
account (http://localhost:9200/myapp/account/1)
========
name
state
groups //groups is an array containing objects like so {id: 1, starred: true}
//the id is the id of the group type
email (http://localhost:9200/myapp/email/1?parent=1)
========
email
primary //just a boolean to denote whether this email is primary or not
group
========
name
description
email
是account
的子级。基于imotov's excellent answer,我可以对
account.name
和email.email
进行搜索,并返回所有account
,其中搜索的前缀与上述两个字段匹配:{
"query": {
"bool": {
"must": [
{
"term": {
"statuses": "active"
}
}
],
"should": [
{
"prefix": {
"name": "a"
}
},
{
"has_child": {
"type": "email",
"query": {
"prefix": {
"email": "a"
}
}
}
}
],
"minimum_number_should_match" : 1
}
}
}
我现在想做的是为每个结果返回2个自定义字段:
email
的字段,如果搜索符合email
类型(它是account
的子代),则返回该电子邮件,否则返回链接到该帐户的primary
电子邮件,如果没有,则可以返回null
。 group
的字段。该字段的值应包含加星号的group
的名称,其ID存储在groups
数组中。本质上:在每个group.id
中找到group.starred
为true的account.groups
,然后根据找到的id从group.name
类型返回匹配的group
。 我一直在看script fields,但是我不确定它是否能够为每个匹配返回字段。我也不确定以上内容在ES中是否可以实现。
有人能提供一些关于这是否可行以及如何开始的指示吗?
最佳答案
当前,根本没有办法访问has_child
或nested
子句中的数据。
唯一的解决方案是获取一些数据,在客户端上做出一些决定,然后获取更多数据。
这是我为实现该目标所做的事情:
{"query":
{"bool":{
"should":{
{
"prefix":{
"email" : "the query"
}
},
{
"terms":{
"_parent" : ["list", "of", "account", "ids"]
}
}
}
}
}
}
根据上述查询,我们可以获得与搜索词匹配的任何电子邮件地址。请记住,将以上查询中的字段设置为包括
_parent
。然后,我们可以使用
array_diff()
或类似PHP之外的语言的类似函数来区分上方的父ID和原始查询。然后,这将为我们提供没有电子邮件匹配的帐户列表。然后,只需发送另一个请求即可获取这些帐户的主要电子邮件。对于组,发送查询以键入
account
并:_id
约束到帐户ID列表。 group.starred
约束为true
。 这将为您提供加星标的列表。要获取更多信息(名称等),请发送查询以键入
group
并执行以下操作:_id
限制为上述组ID。 最后,进行一些客户端处理以将其放在一起,以便程序的下一部分更容易使用。
关于field - 返回一个自定义字段,其中值取决于Elasticsearch中的查询,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11856029/