当前位置: 首页 > 知识库问答 >
问题:

嵌套字段类型的弹性搜索查询

乐正德华
2023-03-14

我试图为一个业务场景制定一个查询,其中我们有一个名为“types”的嵌套字段类型(即类似于字符串的ArrayList)。下面是以“类型”作为字段之一的索引文档示例。

文件1:{“类型”:[{“标签”:“对话”,},{“标签”:“暴力”,},{“标签”:“语言”,}}

文档2:{“类型”:[{“标签”:“对话框”,}}

现在,要求搜索查询最多匹配字段值中的一个值,即如果用户搜索“对话框”,那么它应该只返回文档2,而不是文档1,因为它在字段中存在其他值。基本上,它应该只获取那些与单个搜索查询值完全匹配的记录,不包括字段中存在的所有其他值。

以下是地图:

{
  "media-hub-asset-metadata": {
    "mappings": {
      "dynamic": "true",
      "properties": {
        "Metadata": {
          "properties": {
            "Actors": {
              "type": "text",
              "fields": {
                "keyword": {
                  "type": "keyword",
                  "ignore_above": 256,
                  "normalizer": "lowercase_normalizer"
                },
                "ngram": {
                  "type": "text",
                  "analyzer": "ngram_tokenizer_analyzer"
                }
              }
            },
            "Types": {
              "type": "nested",
              "properties": {
                "Acronym": {
                  "type": "text",
                  "fields": {
                    "keyword": {
                      "type": "keyword",
                      "ignore_above": 256
                    }
                  }
                },
                "Display": {
                  "type": "text",
                  "fields": {
                    "keyword": {
                      "type": "keyword",
                      "ignore_above": 256
                    }
                  }
                },
                "Label": {
                  "type": "text",
                  "fields": {
                    "keyword": {
                      "type": "keyword",
                      "ignore_above": 256,
                      "normalizer": "lowercase_normalizer"
                    },
                    "ngram": {
                      "type": "text",
                      "analyzer": "ngram_tokenizer_analyzer"
                    }
                  }
                },
                "TVLabel": {
                  "type": "text",
                  "fields": {
                    "keyword": {
                      "type": "keyword",
                      "ignore_above": 256,
                      "normalizer": "lowercase_normalizer"
                    },
                    "ngram": {
                      "type": "text",
                      "analyzer": "ngram_tokenizer_analyzer"
                    }
                  }
                }
              }
            }
          }
        },
        "MetadataType": {
          "type": "text",
          "fields": {
            "keyword": {
              "type": "keyword",
              "ignore_above": 256,
              "normalizer": "lowercase_normalizer"
            },
            "ngram": {
              "type": "text",
              "analyzer": "ngram_tokenizer_analyzer"
            }
          }
        },
        "Network": {
          "type": "text",
          "fields": {
            "keyword": {
              "type": "keyword",
              "ignore_above": 256
            }
          }
        }
      }
    }
  }
}

索引文档示例:

{
  "took" : 4,
  "timed_out" : false,
  "_shards" : {
    "total" : 5,
    "successful" : 5,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 9139,
      "relation" : "eq"
    },
    "max_score" : 1.0,
    "hits" : [
      {
        "_index" : "media-hub-asset-metadata",
        "_type" : "_doc",
        "_id" : "1640655|VOD",
        "_score" : 1.0,
        "_source" : {
          "AssetId" : 1640655,
          "MaterialId" : "XMX1311",
          "Metadata" : {
            "Actors" : [
              "Owen, Clive",
              "Mueller-Stahl, Armin",
              "Watts, Naomi"
            ],
            "AirDate" : "2013-05-01T00:00:00Z",
            "ClosedCaption" : true,
            "Code" : "",
            "Types" : [
              {
                "Label" : "Dialog",
                "TVLabel" : "D"
              },
              {
                "Label" : "Violence",
                "TVLabel" : "V"
              },
              {
                "Label" : "Language",
                "TVLabel" : "L"
              }
            ]
          },
          "MetadataType" : "VOD"
        }
      }
    ]
  }
}

非常感谢您的帮助!提前谢谢

共有1个答案

龚振濂
2023-03-14

需要在函数分数查询的同时使用script_score

尝试下面的查询

{
  "query": {
    "function_score": {
      "query": {
        "bool": {
          "must": [
            {
              "nested": {
                "path": "types",
                "query": {
                  "bool": {
                    "must": [
                      {
                        "match": {
                          "types.Label": "Dialog"
                        }
                      }
                    ]
                  }
                }
              }
            }
          ]
        }
      },
      "functions": [
        {
          "script_score": {
            "script": {
              "source": "params._source.containsKey('types') && params._source['types'] != null && params._source.types.size() == 1 ? 1 : 0"
            }
          }
        }
      ],
      "min_score": 0.5             // note this
    }
  }
}

搜索结果将是

"hits": [
      {
        "_index": "67594441",
        "_type": "_doc",
        "_id": "2",
        "_score": 0.53899646,
        "_source": {
          "types": [
            {
              "Label": "Dialog"
            }
          ]
        }
      ]
 类似资料:
  • 我使用的是ES版本5.6。我有一个像下面这样的文档存储在ES中。 我想搜索所有已“启用”的字段。 我尝试了以下查询,但都不起作用。 但是下面的查询起作用了 因此,看起来只匹配顶级字段,而不匹配嵌套字段。是否有任何方法可以查询包含在所有字段中的文本,包括嵌套字段。我不想显式指定嵌套字段名。我正在寻找一种全局搜索,我想在文档中的任何地方搜索“文本”。 谢了。

  • 如何获得空数组和美国的结果和

  • 我有一个弹性搜索索引集合,如下所示, 现在我需要通过将与其值匹配来搜索文档。(是一些字段,其值存储在中)例如。对于字段,如果它是,则应与上述文档匹配。 我尝试将其映射为嵌套对象,但我无法编写查询来搜索与其相应值匹配的2个或更多的键id。

  • 基本问题如下:有没有一种方便的方法可以为嵌套查询的所有字段指定多字段匹配?对于普通查询有效。这在嵌套查询中不起作用,可能是因为嵌套对象没有_all? 下面是更详细的问题: 我有一个名为“Parent”的嵌套文档,如下所示: 这是我用于制作儿童嵌套对象的映射: 这是一个查询,我想使用所有子字段的匹配来选择几个术语查询,以及一个术语查询: 上述查询不起作用,因为我无法为嵌套对象选择多匹配查询中的所有字

  • 我试图获取嵌套文档中有两个名称的文档,但是< code>must子句作为“OR”而不是“AND”工作。下面是一个例子: 映射: 索引3个文档: 我正在寻找在同一文档中与 的文档,使用上述数据只有文档会匹配。我尝试了这个查询: 它与所有文档匹配,因为所有文档都有“John Smith”或“Alice White”。改进此查询以具有两个分离的匹配项,每个值一个匹配器: 那么,我的问题是,如何构建一个查

  • 我已经为一个问题挣扎了一段时间,所以我想我应该通过stackoverflow来解决这个问题。 “我的文档类型”有一个标题、一个语言字段(用于筛选)和一个分组id字段(我省略了所有其他字段以保持重点) 搜索文档时,我希望找到包含标题中文本的所有文档。对于每个唯一的分组id,我只需要一个文档。 我一直在关注tophits聚合,从我所看到的情况来看,它应该能够解决我的问题。 对我的索引运行此查询时: 我