elasticsearch / / 2022. 12. 22. 20:35

elasticsearch nested and 검색

elasticsearch에서 nested 유형에 대해 and조건으로 검색하는 방법이다.

metadata의 nested 유형에 key, value를 값으로 가지는 index를 만든다.

PUT test_nested
{
  "mappings": {
    "properties": {
      "metadata": {
        "type": "nested",
        "properties": {
          "key": {
            "type": "keyword"
          },
          "value": {
            "type": "keyword"
          }
        }
      }
    }
  }
}

아래의 데이터를 입력하자

key value
과일 사과
과일 바나나
식사 비빔밥

위의 조건으로 검색을 해보자.

key = '과일'이고 value = '바나나' 인것은 검색이 되어야 한다.

GET test_nested/_search
{
  "query": {
    "bool": {
      "must": [
        {
          "nested": {
            "path": "metadata",
            "query": {
              "bool": {
                "must": [
                  {
                    "term": {
                      "metadata.key": {
                        "value": "과일"
                      }
                    }
                  },
                  {
                    "term": {
                      "metadata.value": {
                        "value": "바나나"
                      }
                    }
                  }
                ]
              }
            }
          }
        }
      ]
    }
  }
}

[결과]

{
  "took" : 8,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 1,
      "relation" : "eq"
    },
    "max_score" : 1.4508327,
    "hits" : [
      {
        "_index" : "test_nested",
        "_type" : "_doc",
        "_id" : "1",
        "_score" : 1.4508327,
        "_source" : {
          "metadata" : [
            {
              "key" : "과일",
              "value" : "사과"
            },
            {
              "key" : "과일",
              "value" : "바나나"
            },
            {
              "key" : "식사",
              "value" : "비빔밥"
            }
          ]
        }
      }
    ]
  }
}

key = '과일'이고 value = '비빔밥' 인것은 검색이 안되어야 한다.

GET test_nested/_search
{
  "query": {
    "bool": {
      "must": [
        {
          "nested": {
            "path": "metadata",
            "query": {
              "bool": {
                "must": [
                  {
                    "term": {
                      "metadata.key": {
                        "value": "과일"
                      }
                    }
                  },
                  {
                    "term": {
                      "metadata.value": {
                        "value": "비빔밥"
                      }
                    }
                  }
                ]
              }
            }
          }
        }
      ]
    }
  }
}

[결과] 검색이 안된다.

{
  "took" : 7,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 0,
      "relation" : "eq"
    },
    "max_score" : null,
    "hits" : [ ]
  }
}

key = '과일'이고 value = '바나나'
key = '과일'이고 value = '사과'
key = '식사'이고 value = '비빔밥'
인것은 검색이 되어야 한다.

GET test_nested/_search
{
  "query": {
    "bool": {
      "must": [
        {
          "nested": {
            "path": "metadata",
            "query": {
              "bool": {
                "must": [
                  {
                    "term": {
                      "metadata.key": {
                        "value": "과일"
                      }
                    }
                  },
                  {
                    "term": {
                      "metadata.value": {
                        "value": "바나나"
                      }
                    }
                  }
                ]
              }
            }
          }
        },
        {
          "nested": {
            "path": "metadata",
            "query": {
              "bool": {
                "must": [
                  {
                    "term": {
                      "metadata.key": {
                        "value": "과일"
                      }
                    }
                  },
                  {
                    "term": {
                      "metadata.value": {
                        "value": "사과"
                      }
                    }
                  }
                ]
              }
            }
          }
        },
        {
          "nested": {
            "path": "metadata",
            "query": {
              "bool": {
                "must": [
                  {
                    "term": {
                      "metadata.key": {
                        "value": "식사"
                      }
                    }
                  },
                  {
                    "term": {
                      "metadata.value": {
                        "value": "비빔밥"
                      }
                    }
                  }
                ]
              }
            }
          }
        }
      ]
    }
  }
}

[결과] 검색이 잘된다.

{
  "took" : 13,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 1,
      "relation" : "eq"
    },
    "max_score" : 4.8633237,
    "hits" : [
      {
        "_index" : "test_nested",
        "_type" : "_doc",
        "_id" : "1",
        "_score" : 4.8633237,
        "_source" : {
          "metadata" : [
            {
              "key" : "과일",
              "value" : "사과"
            },
            {
              "key" : "과일",
              "value" : "바나나"
            },
            {
              "key" : "식사",
              "value" : "비빔밥"
            }
          ]
        }
      }
    ]
  }
}
반응형
  • 네이버 블로그 공유
  • 네이버 밴드 공유
  • 페이스북 공유
  • 카카오스토리 공유