如何在 OpenSearch(或 Elasticsearch)中查询具有嵌套字段的文档的所有字段?

问题描述 投票:0回答:1

我目前使用的是2.17.1版本并参考了这个官方文档。 OpenSearch - 查询 DSL - 连接查询 - 嵌套查询 - 多级嵌套查询

使用此功能,我可以查询所有术语必须在单个嵌套项目中匹配的结果。

但是在引入嵌套字段之后,我不再能够使用简单的字符串查询(例如“(John)AND(Jane)”)来搜索整个文档中的每个字段。

有没有一种方法可以在项目列表中查询,其中所有术语都必须在单个项目中匹配,以在必要时返回父级,但仍然能够查询整个文档中的术语?

---------更新:长版----------

仍然参考这里的官方文档:OpenSearch - Query DSL - Joining Queries - Nested query - Multi-levelnested query因为这符合我的部分要求。

假设我有一份这样的文档:

  "patient": {
    "name": "John Doe",
    "contacts": [
      {
        "name": "Jane Doe",
        "relationship": "mother",
        "phone": "5551111"
      },
      {
        "name": "Joe Doe",
        "relationship": "father",
        "phone": "5552222"
      }
    ]
  }

当我搜索“jane”和“father”时,我不希望找到此文档,因为尽管这两个术语都存在,但它们位于合同列表中的不同项目中。 我只希望当术语在一项中匹配时找到它,例如搜索“jane”和“mother”时。

据我了解,为了能够查询我的搜索词必须在单个“联系人”中匹配的患者,我必须将它们声明为“嵌套”类型,例如:

  "mappings": {
    "properties": {
      "patient": {
        "type": "nested",
        "properties": {
          "name": {
            "type": "text"
          },
          "contacts": {
            "type": "nested",
            "properties": {
              "name": {
                "type": "text"
              },
              "relationship": {
                "type": "text"
              },
              "phone": {
                "type": "keyword"
              }
            }
          }
        }
      }
    }
  }

使用此映射和嵌套查询,例如:

  "query": {
    "nested": {
      "path": "patient",
      "query": {
        "nested": {
          "path": "patient.contacts",
          "query": {
            "bool": {
              "must": [
                { "match": { "patient.contacts.relationship": "mother" } },
                { "match": { "patient.contacts.name": "Jane" } }
              ]
            }
          }
        }
      }
    }
  }

我完全明白这种行为。

但是我失去了使用字符串查询来查询整个文档的可能性,例如:

   "query": {
     "query_string": {
       "query": "(John) AND (5552222)"
     }
   }
/* 'John' as property of root object of type patient and
   '5552222' as property of one of the contact's properties */

在我引入嵌套字段类型之前,这样的查询可以很好地找到文档,这是需求的第二部分,因为有时我知道哪个术语属于哪个字段并且可以进行嵌套查询,但其他时候我不知道因此无法使用它们并希望回退到对文档的所有字段进行搜索。

这可能吗?也许嵌套类型是错误的方法?使用嵌套类型是否正确,但我需要字符串查询以外的其他内容?

谢谢你,咖啡

elasticsearch opensearch
1个回答
0
投票

要同时搜索多个字段,尤其是单个查询,最好通过将数据保持在同一级别来规范化数据。为此,您可以丰富数据。这是我的建议:

  1. 为每位患者保留一份文档并将其保存为
    text
    字段。
  2. 每个患者有多个联系人作为
    nested
    字段,以确保每个子字段中的关系。

PUT _ingest/pipeline/add_patient_name
{
  "processors": [
    {
      "set": {
        "field": "_temp_patient_name",
        "value": "{{patient.name}}"
      }
    },
    {
      "foreach": {
        "field": "patient.contacts",
        "processor": {
          "set": {
            "field": "_ingest._value.patient_name",
            "value": "{{_temp_patient_name}}"
          }
        }
      }
    },
    {
      "remove": {
        "field": "_temp_patient_name"
      }
    }
  ]
}

PUT hospital
{
  "mappings": {
    "properties": {
      "patient": {
        "properties": {
          "name": {
            "type": "text"
          },
          "contacts": {
            "type": "nested",
            "properties": {
              "name": {
                "type": "text"
              },
              "relationship": {
                "type": "text"
              },
              "phone": {
                "type": "keyword"
              }
            }
          }
        }
      }
    }
  },
  "settings": {
    "index.default_pipeline": "add_patient_name"
  }
}

PUT hospital/_doc/1
{
  "patient": {
    "name": "John Doe",
    "contacts": [
      {
        "name": "Jane Doe",
        "relationship": "mother",
        "phone": "5551111"
      },
      {
        "name": "Joe Doe",
        "relationship": "father",
        "phone": "5552222"
      }
    ]
  }
}

GET hospital/_search
{
  "query": {
    "nested": {
      "path": "patient.contacts",
      "query": {
        "query_string": {
          "default_field": "*",
          "query": "John AND 5552222"
        }
      }
    }
  }
}

ingest pipeline

© www.soinside.com 2019 - 2024. All rights reserved.