#ruby-on-rails #elasticsearch #elasticsearch-rails
#ruby-on-rails #elasticsearch #elasticsearch-rails
Вопрос:
Я создаю веб-приложение Rails с помощью elasticsearch-model gem. Я хотел бы создать поисковый запрос с фильтрацией для моей модели места. Мне удалось выполнить поиск по имени, однако я хотел бы иметь возможность фильтровать свой поиск по городу (в данном примере Лондон).
На данный момент мой запрос выглядит следующим образом:
"query": {
"bool": {
"must": {
"match": {
"name": {
"query": term,
"operator": "and",
"fuzziness": 1
}
}
},
"filter": {
"term": {
"city": "London"
}
}
}
}
и чем я просто вызываю Place.search("here goes query").records.to_a
без фильтра поиск деталей работает нормально, но когда я добавляю фильтр, я не получаю никакого результата.
Это сопоставление для поиска места:
settings analysis: {
filter: {
ngram_filter: {
type: "nGram",
min_gram: 2,
max_gram: 20
}
},
analyzer: {
ngram_analyzer: {
type: "custom",
tokenizer: "standard",
filter: [
"lowercase",
"asciifolding",
"ngram_filter"
]
},
whitespace_analyzer: {
type: "custom",
tokenizer: "whitespace",
filter: [
"lowercase",
"asciifolding"
]
}
}
} do
mappings dynamic: 'false' do
indexes :name,
type: "string",
analyzer: "ngram_analyzer",
search_analyzer: "whitespace_analyzer"
Вот ссылка, которую я использовал, чтобы узнать, как фильтровать: документ Elasticsearch
Комментарии:
1. Одна из распространенных ошибок заключается в том, что данные разбиваются на то, что Elastic Search называет «токенами», на основе существующего токенизатора, и фильтр должен соответствовать токенам, которые они создают, а не тем, какие данные были первоначально проиндексированы. Например, после индексации поля со значением «AD-13» у меня были токены «ad» и «13», и поэтому «AD-13» не дал никаких результатов.
2. Я думаю, что я немного исправил, добавил
indexes :city, type: "string"
. Однако он работает только с городом, который состоит из одного слова и имеет нижний регистр, я думаю, что мне нужно поработать с анализатором, чтобы исправить это.3. Анализатор, безусловно, является проблемой. Вы можете указать не анализировать поля, что я и сделал, чтобы избежать разбиения значений с пробелами на отдельные токены, что приводит к неправильному поиску.
Ответ №1:
Мне пришлось определить в сопоставлении тип города со строкой и не выполнять какой-либо анализ этого поля при создании токенов.
Итак, в сопоставлении я добавил:
indexes :city,
type: "string",
index: "not_analyzed"