【问题标题】:Elastic search : How to search in two documents in single index?弹性搜索:如何在单个索引中搜索两个文档?
【发布时间】:2020-04-23 23:29:28
【问题描述】:

我在一个名为inventory 的索引中配置了两个文档。

  1. 个人资料(有用户和手机信息)
  2. p2p 关系

库存索引映射属性如下:

{
    "mappings": {
        "properties": {
            "type": {"type": "keyword"},
            "id": {"type": "keyword"},
            "sourceId": {"type": "keyword"},
            "targetId": {"type": "keyword"},
            "firstName": {"type": "text"},
            "lastName": {"type": "text"},
            "createdBy": {"type": "text"},
            "p_type": {"type": "text"},
            "model": {"type": "text"},
            "OS": {"type": "keyword"}
            }
        }
}

个人资料有以下信息

用户:

{   "type":"profile",   "id" : "user1", "p_type" : "user",  "firstName" : "Ashok", "lastName" : "S" }
{   "type":"profile",   "id" : "user2", "p_type" : "user",  "firstName" : "Arun", "lastName" : "V" }

手机:

{   "type":"profile",   "id" : "mobile1", "p_type" : "mobile",  "model" : "samsung", "OS" : "Android" }
{   "type":"profile",   "id" : "mobile2", "p_type" : "mobile",  "model" : "iPhone", "OS" : "iOS" }

p2p-relation有哪个用户使用了哪个手机信息:

{   "type":"p2p-relation",  "id" : "user1-owns-mobile1", "sourceId" : "user1",  "targetId" : "mobile1", "createdBy" : "admin" }
{   "type":"p2p-relation",  "id" : "user1-owns-mobile2", "sourceId" : "user1",  "targetId" : "mobile2", "createdBy" : "admin" }

在我们的业务案例中,我们需要检索用户拥有的 android/iOS 手机列表,该列表是我们从客户那里获得的输入。

也就是说,如果 user1 请求 /mymobiles?query=os==Android ,它应该将其翻译成 ES 并期待

{ “type”:“profile”,“id”:“mobile1”,“p_type”:“mobile”,“model”:“samsung”,“OS”:“Android”}

作为结果,如果 user2 请求相同,它应该返回空。

我尝试过查询和布尔。但它只在单个文档中搜索。如何在弹性搜索中实现这一点?

【问题讨论】:

  • 你能分享你的索引映射吗?这些types、profile和p2p-relation是同一个索引的一部分,或者它们是不同类型的ES索引,你使用的是哪个版本的elastic?
  • “profile”和“p2p-relation”都存储在同一个索引中。并使用 7.4.0 版本。
  • 用索引映射更新了问题。
  • 我在你的映射中没有看到p_type
  • 对不起。我会在映射中更新它。 p_type、模型和操作系统也存在于映射中。

标签: java elasticsearch elasticsearch-query


【解决方案1】:

上述模型属于多对多关系数据模型。一个用户可以有许多移动电话分配给他,并且移动设备可以在一段时间内分配给许多用户。 因此将数据模型更改为将其存储为嵌套对象。

{
  "mappings": {
    "properties": {
        "type": {"type": "keyword"},
        "id": {"type": "keyword"},
        "firstName": {"type": "text"},
        "lastName": {"type": "text"},
        "createdBy": {"type": "text"},
        "model": {"type": "text"},
        "OS": {"type": "keyword"},
        "mobiles" : {
            "type" : "nested",
            "properties" : {
                "id": {"type": "keyword"},
                "model": {"type": "text"},
                "OS": {"type": "keyword"},
                "createdBy": {"type": "text"}
            }
        },
        "users" : {
            "type" : "nested",
            "properties" : {
                "id": {"type": "keyword"},
                "firstName": {"type": "keyword"},
                "lastName": {"type": "keyword"},
                "createdBy": {"type": "text"}                               
            }
        }
}}}

但痛苦的是,每当将手机分配给用户时,我都要花费额外的精力来更新两行。

数据存储如下

{   "type":"profile",   "id" : "user1",  "firstName" : "Ashok", "lastName" : "S", "mobiles" : [ {"id" : "uuid1", "model": "samsung", "OS" : "Android"}] }

{   "type":"profile",   {"id" : "uuid1", "model": "samsung", "OS" : "Android"}, "users" : [ "id" : "user1",  "firstName" : "Ashok", "lastName" : "S"] }

为了回答 /mymobiles?query=os==Android,我使用了以下查询。

{ 
"query": {
    "bool": {
        "must": [ 
            {
              { "term": {"OS": "android"} },
              "nested": {
                "path": "users",
                "query": {
                  "bool": {
                    "must": [ {"term": {"users.id": "user1"} }]
                  }
                }
              }
            }
        ]   
    }
}}

我参考了以下链接来执行此操作:https://medium.com/@mena.meseha/briefly-describe-how-to-store-complex-relational-data-in-elasticsearch-f30277317b1

【讨论】:

    猜你喜欢
    • 2015-12-18
    • 1970-01-01
    • 1970-01-01
    • 2015-06-01
    • 1970-01-01
    • 2016-10-08
    • 2022-08-12
    • 2021-05-18
    • 2017-02-28
    相关资源
    最近更新 更多