Elasticsearch соответствует всем запросам, используя Java API - PullRequest
3 голосов
/ 27 апреля 2020

Мы используем Elasticsearch версии 7.3.1 и Java API.

Мы реализуем «бесплатный поиск», что означает поиск значения в ALL полях в каждый сегмент в Elasticsearch. Если это значение появляется хотя бы в одном из полей сегмента, оно должно быть возвращено.

До сих пор мы использовали следующее: QueryBuilders.multiMatchQuery(value) и оно работало хорошо.

На сегодняшний день , мы добавили в файл отображения некоторые вложенные (тип данных Elasticsearch) поля.

После этого изменения приведенный выше код больше не возвращает ожидаемых результатов.

Как реализовать поиск в ВСЕХ полях в сегменте без указания каждого поля для поиска?

1 Ответ

5 голосов
/ 27 апреля 2020

Вы могли бы реализовать логику c всех предыдущих версийasticsearch (я полагаю, это было удалено после версии 6).

PUT stackoverflow
{
  "mappings": {
    "properties": {
      "all": {
        "type": "text"
      },
      "group": {
        "type": "text",
        "copy_to": "all"
      },
      "user": {
        "type": "nested",
        "properties": {
          "email": {
            "type": "keyword",
            "copy_to": "all"
          },
          "info": {
            "type": "text",
            "copy_to": "all"
          }
        }
      }
    }
  }
}

Обычно вы добавляете параметр copy_to.

PUT stackoverflow/_doc/1
{
  "group" : "programmers",
  "user" : [
    {
      "email" : "test@gmail.com",
      "info" :  "java developer"
    },
    {
      "email" : "demo@wikipedia.org",
      "info" :  "css guru"
    }
  ]
}

Затем вы можете выполнить поиск по полю all

GET stackoverflow/_search
{
  "query": {
    "match": {
      "all": "guru"
    }
  }
}

Обновление

Вот пример того, как изменить ваш запрос для того, чтобы он работал без copy_to

GET stackoverflow/_search
{
  "query": {
    "bool": {
      "minimum_should_match": 1,
      "should": [
        {
          "multi_match": {
            "query": "SEARCH_INPUT_HERE",
            "fields": [
              "group"
            ]
          }
        },
        {
          "nested": {
            "path": "user",
            "query": {
              "multi_match": {
                "query": "SEARCH_INPUT_HERE",
                "fields": [
                  "user.email", "user.info"
                ]
              }
            }
          }
        }
      ]
    }
  }
}

Обновление 2

public static void main(String[] args) {
    String queryInput = "QUERY_INPUT_HERE";
    String[] nested = {"user", "product"};

    MultiMatchQueryBuilder multiMatchQueryBuilder = QueryBuilders.multiMatchQuery(queryInput, "*");

    BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery();
    List<QueryBuilder> shouldQueryBuilders = boolQueryBuilder.should();

    shouldQueryBuilders.add(multiMatchQueryBuilder);
    for(String path : nested) {
        NestedQueryBuilder nestedQueryBuilder = QueryBuilders.nestedQuery(path, multiMatchQueryBuilder, ScoreMode.Avg);
        shouldQueryBuilders.add(nestedQueryBuilder);
    }

    SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
    searchSourceBuilder.query(boolQueryBuilder);

    SearchRequest searchRequest = new SearchRequest();
    searchRequest.source(searchSourceBuilder);
    searchRequest.indices("MY_INDEX");

    System.out.println(searchRequest.toString());
}

Вывод

{
  "query": {
    "bool": {
      "should": [
        {
          "multi_match": {
            "query": "QUERY_INPUT_HERE",
            "fields": [
              "*^1.0"
            ],
            "type": "best_fields",
            "operator": "OR",
            "slop": 0,
            "prefix_length": 0,
            "max_expansions": 50,
            "zero_terms_query": "NONE",
            "auto_generate_synonyms_phrase_query": true,
            "fuzzy_transpositions": true,
            "boost": 1.0
          }
        },
        {
          "nested": {
            "query": {
              "multi_match": {
                "query": "QUERY_INPUT_HERE",
                "fields": [
                  "*^1.0"
                ],
                "type": "best_fields",
                "operator": "OR",
                "slop": 0,
                "prefix_length": 0,
                "max_expansions": 50,
                "zero_terms_query": "NONE",
                "auto_generate_synonyms_phrase_query": true,
                "fuzzy_transpositions": true,
                "boost": 1.0
              }
            },
            "path": "user",
            "ignore_unmapped": false,
            "score_mode": "avg",
            "boost": 1.0
          }
        },
        {
          "nested": {
            "query": {
              "multi_match": {
                "query": "QUERY_INPUT_HERE",
                "fields": [
                  "*^1.0"
                ],
                "type": "best_fields",
                "operator": "OR",
                "slop": 0,
                "prefix_length": 0,
                "max_expansions": 50,
                "zero_terms_query": "NONE",
                "auto_generate_synonyms_phrase_query": true,
                "fuzzy_transpositions": true,
                "boost": 1.0
              }
            },
            "path": "product",
            "ignore_unmapped": false,
            "score_mode": "avg",
            "boost": 1.0
          }
        }
      ],
      "adjust_pure_negative": true,
      "boost": 1.0
    }
  }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...