目录
全文检索框架以及搜索引擎的使用
在实际项目中,会遇到很多在搜索栏输入查询的需求,比如淘宝京东的搜索功能。
全文检索不同于特定字段的模糊查询,使用全文检索的效率更高。
搜索引擎能够对表中的某些字段进行关键词分析,建立关键词对应的索引数据,并且能够对于中文进行分词处理。
全文搜索框架可以帮助用户使用搜索引擎。
下面介绍一种项目中使用过的框架:
-
haystack:全文检索的框架,支持whoosh、solr、Xapian、Elasticsearc四种全文检索引擎。
-
whoosh:纯Python编写的全文搜索引擎,虽然性能比不上sphinx、xapian、Elasticsearc等,但是无二进制包,程序不会莫名其妙的崩溃,对于小型的站点,whoosh已经足够使用。
-
jieba:一款免费的中文分词包,如果觉得不好用可以使用一些收费产品。
1. 安装与配置
1) Python包的安装
pip install django-haystack(注意和django版本的兼容问题)
pip install whoosh
2) 在settings.py文件的配置。
INSTALLED_APPS = [
...
"""
1. 注册app
"""
'haystack'
]
"""
2. 全文检索haystack框架配置
"""
HAYSTACK_CONNECTIONS = {
'default': {
# 使用whoosh引擎
'ENGINE': 'haystack.backends.whoosh_backend.WhooshEngine',
# 索引文件路径
'PATH': os.path.join(BASE_DIR, 'whoosh_index'),
}
}
# 当数据库表 添加、修改、删除数据时,自动生成索引
HAYSTACK_SIGNAL_PROCESSOR = 'haystack.signals.RealtimeSignalProcessor'
2. 创建引擎及索引
1) 项目下创建search_indexes.py
文件,并在此文件中创建引擎和索引(固定写法和用法)。
# 定义索引类
from haystack import indexes
# 导入你的模型类
from apps.goods.models import GoodsSKU
# 指定对于某个类的某些数据建立索引
# 索引类名格式:模型类名+Index
class GoodsSKUIndex(indexes.SearchIndex, indexes.Indexable):
# 索引字段 use_template=True指定根据表中的哪些字段建立索引文件的说明放在一个文件中
text = indexes.CharField(document=True, use_template=True)
def get_model(self):
# 返回你的模型类
return GoodsSKU
# 建立索引的数据
def index_queryset(self, using=None):
return self.get_model().objects.all()
2) 创建索引文件
在templates模板目录下创建search/indexes/goods/goodssku_text.txt文件(search/indexes/模块名/模型类_text.txt
固定写法),并在goodssku_text.txt文件中,指定哪些表字段用于创建索引.
# goodssku_text.txt
# 指定数据库表中哪些字段来建立索引
{{object.name}} # 商品名称
{{object.desc}} # 商品简介
{{object.goods.detail}} # 商品详情
3) 生成索引文件
python manage.py rebuild_index
在settings配置中索引文件的路径为’PATH’: os.path.join(BASE_DIR, ‘whoosh_index’),也就是项目目录下的whoosh_index目录,此时查看项目目录下已经成功创建该目录,并在该目录下生成了goods_sku表的索引文件.
3. 索引文件的使用
1) 前端使用
找到搜索框,进行如下编写,需要注意的是表单提交的方法为get
以及text input输入框的name必须为q
,这两个为固定的。
<form method="get" action="/search/">
<input type="text" class="input_text fl" name="q" placeholder="搜索商品">
<input type="submit" class="input_btn fr" name="" value="搜索">
</form>
2) 路由配置
在根基urls文件中,配置全文检索框架
url(r'^search/', include('haystack.urls')), # 全文检索框架
3) 启动项目,点击搜索栏按钮
提示如下错误,在templates/search目录下找不到search.html文件:
解决:
在templates/search目录下创建search.html文件,将list.html(搜索后要展示的页面)模板中的内容拷贝到该文件中,进行修改显示出搜索结果列表页,haystack会把搜索出的结果传递给该路径下的search.html模板。
-
query:搜索关键字
-
page:当前页的page对象 –>遍历page对象,获取到的是SearchResult类的实例对象,对象的属性object才是模型类的对象
-
paginator:分页paginator对象
4. 改变分词方式
由于很多词搜索不到,我们使用中文分词包,更改whoosh默认分词方式。
1) 安装jieba分词包
pip install jieba
2) 创建ChineseAnalyzer.py文件
找到虚拟环境路径下(D:\Python36\Lib\site-packages\haystack\backends),在该路径下创建ChineseAnalyzer.py文件,文件内容如下:
import jieba
from whoosh.analysis import Tokenizer, Token
class ChineseTokenizer(Tokenizer):
def __call__(self, value, positions=False, chars=False,
keeporiginal=False, removestops=True,
start_pos=0, start_char=0, mode='', **kwargs):
t = Token(positions, chars, removestops=removestops, mode=mode, **kwargs)
seglist = jieba.cut(value, cut_all=True)
for w in seglist:
t.original = t.text = w
t.boost = 1.0
if positions:
t.pos = start_pos + value.find(w)
if chars:
t.startchar = start_char + value.find(w)
t.endchar = start_char + value.find(w) + len(w)
yield t
def ChineseAnalyzer():
return ChineseTokenizer()
4) 更改whoosh_backend.py文件
(D:\Python36\Lib\site-packages\haystack\backends路径下)
复制whoosh_backend.py文件,改为whoosh_cn_backend.py,编辑该文件,导入from .ChineseAnalyzer import ChineseAnalyzer
类,将代码中的analyzer=StemmingAnalyzer()
修改为analyzer=ChineseAnalyzer()
from .ChineseAnalyzer import ChineseAnalyzer
analyzer=ChineseAnalyzer()
修改settings中haystack配置,将.whoosh_backend改为.whoosh_cn_backend
HAYSTACK_CONNECTIONS = {
'default': {
# 使用whoosh引擎
'ENGINE': 'haystack.backends.whoosh_cn_backend.WhooshEngine',
# 索引文件路径
'PATH': os.path.join(BASE_DIR, 'whoosh_index'),
}
}