使用haystack实现Django的全文搜索 --Whoosh+Jieba搜索引擎

安装haystack和Whoosh

pip install drf-haystack
pip install whoosh
pip install jieba  # Whoosh只支持英文分词搜索,不支持中文的分词,所以我们需要使用Jieba进行中文分词

django-haystack的配置 Whoosh搜索引擎

修改settings.py文件,添加haystack应用:

INSTALLED_APPS = (
  ...
  'haystack', #将haystack放在最后
)
在settings中追加haystack的相关配置:

HAYSTACK_CONNECTIONS = {
  'default': {
    'ENGINE': 'haystack.backends.whoosh_cn_backend.WhooshEngine',
    'PATH': os.path.join(BASE_DIR, 'whoosh_index'),
  }
}
# 添加此项,当数据库改变时,会自动更新索引,非常方便
HAYSTACK_SIGNAL_PROCESSOR = 'haystack.signals.RealtimeSignalProcessor'

在应用目录下,添加一个索引类

在子应用的目录下,创建一个名为 search_indexes.py 的文件。

from haystack import indexes
 ① # 修改此处,改成你自己的model
from goods.models import Goods    (Goods是子应用goods中的一个模型类) 

② #修改此处,类名为模型类的名称+Index,比如模型类为Goods,则这里类名为GoodsIndex
class GoodsIndex(indexes.SearchIndex, indexes.Indexable):
    # 指明哪些字段产生索引,产生索引的字段,会作为前端检索查询的关键字;
    # document是指明text是使用的文档格式,产生字段的内容在文档中进行描述;
    # use_template是指明在模板中被声明需要产生索引;
    text = indexes.CharField(document=True, use_template=True)

③ # 此外可以存在,可以不存在,看具体需要的数据
    """下面这些字段,在索引类中进行申明,在REST framework中,索引类的字段可以被作为索引查询结果返回数据额来源"""
    id = indexes.IntegerField(model_attr='id')
    name = indexes.CharField(model_attr='name')
    price = indexes.DecimalField(model_attr='price')

    """也就是说,前端在索引的时候,可以按照text=xxx,也可以按照id=xxx,name=xxx等,我们的数据返回也是返回id,name,price """

④ # 修改此处,返回的是你自己的model
    def get_model(self):
        """获取模型类"""
        return Goods
        
⑤# 修改return 可以修改返回查询集的内容,比如返回时,有什么条件限制的时候
    def index_queryset(self, using=None):
        """声明满足索引要求的返回的查询集"""
        return Goods.objects.all()

1.在进行索引类的使用时,修改上述代码中的①②③④⑤即可;
2.此文件指定如何通过已有数据来建立索引。get_model处,直接将django中的model放过来,便可以直接完成索引啦,无需关注数据库读取、索引建立等细节。
3.text=indexes.CharField一句,指定了将模型类中的哪些字段建立索引,而use_template=True说明后续我们还要指定一个模板文件,告知具体是哪些字段;

指定索引模板文件

在项目的“templates/search/indexes/应用名称/”下创建“模型类名称_text.txt”文件。

例如,上面的模型类名称为GoodsInfo,则创建goodsinfo_text.txt(全小写即可),此文件指定将模型中的哪些字段建立索引,写入如下内容:(只修改中文,不要改掉object)

{ { object.字段1 }}
{ { object.字段2 }}
{ { object.字段3 }}

haystack视图函数和序列化器(DRF中自带的):

序列化器

from drf_haystack.serializers import HaystackSerializer

class GoodsIndexSerializer(HaystackSerializer):
    """
    Goods索引结果数据序列化器
    """
    class Meta:
        index_classes = [GoodsIndex]
        fields = ('text', 'id', 'name', 'price')

视图

from drf_haystack.viewsets import HaystackViewSet

class GoodsSearchViewSet(HaystackViewSet):
    """
    Goods搜索
    """
    index_models = [Goods]

    serializer_class = GoodsIndexSerializer

添加url

在整个项目的urls.py中,配置搜索功能的url路径:

from rest_framework.routers import DefaultRouter

router = DefaultRouter()
router.register('skus/search', views.SKUSearchViewSet, base_name='skus_search')
urlpatterns += router.urls

使用jieba中文分词器

我的 whoosh_backend.py 的存在路径,找不到的话,可以使用 pip install django-haystack 如果你安装过了,他会提示你具体的安装路径的;
在这里插入图片描述

首先先将…/Lib/site-packages/haystack/backends目录中的whoosh_backend.py文件复制到app目录下并改名为whoosh_cn_backend.py,这个文件名要和setting文件中配置中ENGIN的一样,当然,我们不是全部都修改这个文件,修改的仅仅是期中的个别位置,修改的地方如下:(TEXT大概在162行)

#在全局引入的最后一行加入jieba分词器
from jieba.analyse import ChineseAnalyzer
 
#修改
schema_fields[field_class.index_fieldname] = TEXT(stored=True, analyzer=ChineseAnalyzer(),
 field_boost=field_class.boost, sortable=True)

拓展

Elasticsearch搜索引擎

你可能感兴趣的:(Django扩展,搜索引擎,whoosh,jieba)