Django 干草堆和嗖嗖声的字符折叠

Posted

技术标签:

【中文标题】Django 干草堆和嗖嗖声的字符折叠【英文标题】:Character folding for a Django haystack and whoosh 【发布时间】:2014-01-09 05:39:40 【问题描述】:

我有一个基于 django 的应用程序,带有 haystack 和 whoosh 搜索引擎。我想提供与重音和特殊字符无关的搜索,以便我也可以通过使用不带特殊字符的单词来查找带有特殊字符的索引数据:

索引为:

'café'

搜索词:

'cafe'  
'café'

我已经编写了一个特定的 FoldingWhooshSearchBackend,它使用 StemmingAnalyzer 和 aCharsetFilter(accent_map),如以下文档中所述:

https://gist.github.com/gregplaysguitar/1727204

但是搜索仍然无法正常工作,即我无法使用“cafe”进行搜索并找到“café”。我使用以下方法查看了搜索索引:

from whoosh.index import open_dir
ix = open_dir('myservice/settings/whoosh_index')
searcher = ix.searcher()
for doc in searcher.documents():
    print doc

特殊字符仍在索引中。

我需要做一些额外的事情吗?是关于更改索引模板的吗?

【问题讨论】:

仅供参考,我更新了这个要点,它适用于 Haystack 2.4.0 和 Whoosh 2.7.0。我不确定你的问题是什么,但我最初写它的方式相当脆弱,所以也许这就是问题所在。 【参考方案1】:

我认为最好的方法是让 Haystack 创建架构以实现最大的前向兼容性,然后将 CharsetFilter 破解。

此代码适用于 Haystack 2.4.0 和 Whoosh 2.7.0:

from haystack.backends.whoosh_backend import WhooshEngine, WhooshSearchBackend
from whoosh.analysis import CharsetFilter, StemmingAnalyzer
from whoosh.support.charset import accent_map
from whoosh.fields import TEXT


class FoldingWhooshSearchBackend(WhooshSearchBackend):

    def build_schema(self, fields):
        schema = super(FoldingWhooshSearchBackend, self).build_schema(fields)

        for name, field in schema[1].items():
            if isinstance(field, TEXT):
                field.analyzer = StemmingAnalyzer() | CharsetFilter(accent_map)

        return schema


class FoldingWhooshEngine(WhooshEngine):
    backend = FoldingWhooshSearchBackend

【讨论】:

【参考方案2】:

您必须为您的模型编写Haystack SearchIndex 类。这就是您可以为搜索索引准备模型数据的方式。

myapp/search_index.py 示例:

from haystack import site
from haystack import indexes

class UserProfileIndex(indexes.SearchIndex):
    text = indexes.CharField(document=True)

    def prepare_text(self, obj):
        data = [obj.get_full_name(), obj.user.email, obj.phone]
        original = ' '.join(data)
        slugified = slugify(original)
        return ' '.join([original, slugified])

site.register(UserProfile, UserProfileIndex)

如果用户的姓名为café,您将找到他的个人资料,其中包含cafécafe 两个搜索词。

【讨论】:

谢谢!这似乎可以解决问题。但是,我已经在自定义后端使用了字符集过滤器和词干分析器。这个后端没用吗? 不,搜索后端应该能够处理它。自定义 SearchIndex 是错误的方法,因为它不会对用户的输入数据做任何事情。

以上是关于Django 干草堆和嗖嗖声的字符折叠的主要内容,如果未能解决你的问题,请参考以下文章

django 管理界面 - 如何在更改列表视图中折叠/展开对象详细信息?

python测试开发django-188.Bootstrap折叠(Collapse)插件

如何在 django 模板的引导程序中创建可折叠卡片?

Django Admin Kink 与折叠字段集

将包含子字符串的多行折叠成一行

一键打开多个引导折叠面板[重复]