Как экранировать спецсимвол из запроса `match_phase`? - PullRequest
0 голосов
/ 20 января 2020

Я использую elasticsearch 6.8 и выполняю запрос ниже:

curl localhost:9200/twitter/_search?pretty=true -H 'Content-Type: application/json' -d '
{ "query": {"match_phrase": { "name": ".C" }}}'
{
  "took" : 2,
  "timed_out" : false,
  "_shards" : {
    "total" : 5,
    "successful" : 5,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : 2,
    "max_score" : 0.2876821,
    "hits" : [
      {
        "_index" : "twitter",
        "_type" : "1",
        "_id" : "2",
        "_score" : 0.2876821,
        "_source" : {
          "name" : "my name C 100"
        }
      },
      {
        "_index" : "twitter",
        "_type" : "1",
        "_id" : "1",
        "_score" : 0.2876821,
        "_source" : {
          "name" : "my name .C 100"
        }
      }
    ]
  }
}

Вы видите, что возвращаются два документа, но я не ожидаю, что первый, который не получил .C, будет возвращен. Я попытался сбежать dot с {"match_phrase": { "name": "\\.C" }}, но это не сработало.

Я не хочу менять тип name на keyword, потому что мне все еще нужен токенизатор.

И я поставил . в качестве защищенных слов в настройках индекса, как показано ниже:

#curl localhost:9200/twitter/_settings?
{
  "twitter" : {
    "settings" : {
      "index" : {
        "number_of_shards" : "5",
        "provided_name" : "twitter",
        "creation_date" : "1579489541087",
        "analysis" : {
          "filter" : {
            "word_delim_filter" : {
              "type" : "word_delimiter",
              "protected_words" : [
                "."
              ]
            }
          },
          "analyzer" : {
            "content" : {
              "type" : "custom",
              "tokenizer" : "whitespace"
            },
            "custom_synonyms_delim" : {
              "filter" : [
                "word_delim_filter"
              ],
              "tokenizer" : "whitespace"
            }
          }
        },
        "number_of_replicas" : "1",
        "uuid" : "nYr7NPdVRCqIcTzzM_iBeQ",
        "version" : {
          "created" : "6080299"
        }
      }
    }
  }
}

Как мне выбрать dot в запросе?

1 Ответ

0 голосов
/ 21 января 2020

Вот рабочий пример того, как обрабатывать dot в вашем сценарии:

Отображение

PUT my_index
{
  "settings": {
    "analysis": {
      "filter": {
        "word_delim_filter": {
          "type": "word_delimiter",
          "type_table": [
            ". => ALPHANUM"
          ]
        }
      },
      "analyzer": {
        "content": {
          "type": "custom",
          "tokenizer": "whitespace"
        },
        "custom_synonyms_delim": {
          "filter": [
            "word_delim_filter"
          ],
          "type": "custom",
          "tokenizer": "keyword"
        }
      }
    }
  },
  "mappings": {
    "_doc": {
      "properties": {
        "name": {
          "type": "text",
          "analyzer": "custom_synonyms_delim",
          "fields": {
            "keyword": {
              "type": "keyword",
              "ignore_above": 256
            }
          }
        }
      }
    }
  }
}

Индексирование документов

POST my_index/_doc/1
{
  "name" : "my name C 100"
}

POST my_index/_doc/2
{
  "name" : "my name .C 100"
}

Поисковый запрос

GET my_index/_search
{
  "query": {
    "match_phrase": {
      "name": ".C"
    }
  }
}

Результаты

"hits" : [
      {
        "_index" : "my_index",
        "_type" : "_doc",
        "_id" : "2",
        "_score" : 0.6931472,
        "_source" : {
          "name" : "my name .C 100"
        }
      }
    ]

Надеюсь, это поможет

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...