鉴于我有一个模特
class Firm < ActiveRecord::Base
searchable do
text :name
end
end
solr的schema.xml包含
<fieldType name="text" class="solr.TextField" omitNorms="false">
<analyzer>
<tokenizer class="solr.StandardTokenizerFactory"/>
<filter class="solr.StandardFilterFactory"/>
<filter class="solr.LowerCaseFilterFactory"/>
<filter class="solr.NGramFilterFactory" minGramSize="2" maxGramSize="30"/>
</analyzer>
<analyzer type="query">
<tokenizer class="solr.StandardTokenizerFactory"/>
<filter class="solr.StandardFilterFactory"/>
<filter class="solr.LowerCaseFilterFactory"/>
</analyzer>
</fieldType>
我有一个名字=='Ойл-М(Oil-M)'的公司
当我尝试搜索时
Sunspot.search(Firm) do
fulltext 'Ойл-М'
end
然后我什么都没得到
当我尝试搜索时
Sunspot.search(Firm) do
fulltext 'Ойл'
end
然后我需要坚定
如何设置Solr和/或搜索以便能够通过两个查询找到此公司?
答案 0 :(得分:3)
你的NGramFilter正在切断最后的'M',因为你有minGramSize=2
。设置minGramSize=1
会起作用,但这会大大增加Solr必须存储的数据大小,并且还会增加噪音。
索引并查询Solr中的字段时,会发生两件事:
单独进行索引和查询。
在这种情况下,您使用StandardTokenizerFactory,StandardFilter,LowercaseFilter和NGramFilter索引字段,并使用除NGramFilter之外的所有内容查询字段。
当您将“Ойл-М(Oil-M)”索引到Solr时,会发生什么。
StandardTokenizerFactory: ['Ойл', 'М', 'Oil', 'M']
StandardFilter: ['Ойл', 'М', 'Oil', 'M']
LowerCaseFilter: ['ойл', 'м', 'oil', 'm']
NGramFilter: ['ой', 'йл', 'ойл', 'oi', 'il', 'oil']
'm'完全消失了。搜索“Ойл-М”不会返回任何内容,因为没有 M
来搜索。
切除NGramFilter,除非你有充分的理由使用它,并坚持使用标准的俄罗斯fieldType。
<fieldType name="text_ru" class="solr.TextField" positionIncrementGap="100">
<analyzer>
<tokenizer class="solr.StandardTokenizerFactory"/>
<filter class="solr.LowerCaseFilterFactory"/>
<filter class="solr.StopFilterFactory" ignoreCase="true" words="lang/stopwords_ru.txt" format="snowball" enablePositionIncrements="~
<filter class="solr.SnowballPorterFilterFactory" language="Russian"/>
</analyzer>
</fieldType>
注意:请注意,索引分析器和查询分析器之间没有区别。每个查询的转换方式与索引时完全相同。