107、【Ubuntu】【Hugo】搭建私人博客:模糊搜索 Fuse.js(三)

【声明】本博客所有内容均为个人业余时间创作,所述技术案例均来自公开开源项目(如Github,Apache基金会),不涉及任何企业机密或未公开技术,如有侵权请联系删除

背景

上篇 blog
【Ubuntu】【Hugo】搭建私人博客:模糊搜索 Fuse.js(二)

分析了模糊搜索的概念,以及 Fuse.js 的核心原理,下面继续

搭建私人博客

OK,接下来继续看 fastsearch.js 的实现

当解析到 JSON 内容后,这里定义了 Fuse.js 的几个核心配置选项,这些选项将决定搜索如何匹配关键词,下面详细说下这里的选项:

  • keys定义在哪些字段中搜索 ,这里默认值是 ['title', 'permalink', 'summary', 'content'],用户输入的关键词会在这几个字段里面匹配
  • threshold:匹配阈值,这里默认值 0.4,范围(0.0 ~ 1.0),其中
    0.0 = 完全精确匹配
    0.4 = 允许较多错误,比如漏字,顺序错等
    1.0 = 任意字符都算匹配(不推荐)
  • distance:模糊匹配半径,默认值 100,需要配合关键词 location 来使用,表示关键词偏离理想位置多远仍可以接受,不过这里 ignoreLocation 为 true,那 location 参数就没啥影响
  • ignoreLocation:是否忽略关键词在文本中的位置,默认值 true
    true:全文平等对待,适合博客这样的全文搜索
    false:优先匹配开头,适合命令,文件名的搜索方式

这套默认配置很适合博客或者文档站点,因为用户可能记不清完整标题,但关键词还是记得几个的

OK,下面继续看下面的用户自定义配置

前面 blog 说过,import * as params... 表示从 Hugo 构建系统(hugo.toml 配置文件)导入配置参数

这是 Hugo 的 JS 构建管道特性,在模板中,可以把站点配置传入 JS,比如

go 复制代码
{{ $searchJS := resources.Get "search.js" | js.Build (dict "params" .Site.Params.search) }}

比如 Hugo PaperMod 是在 head.html 模板中传入站点配置的

然后可以在 Hugo 自定义配置文件 hugo.toml 中定义

yaml 复制代码
params:
  search:
    fuseOpts:
      threshold: 0.3
      keys: ["title", "tags"]

另外,这里的 ?? 有点类似 C 语言的三元运算符用法

x: a ?? b 是空值合并运算符,如果 anull 或者 undefined,就用 b 作为 x 的值,这样既允许用户覆盖,又可以保留安全默认值,下面来详细说下里面的自定义选项

  • isCaseSensitive:表示是否区分大小写,用户没定义的话,默认 false
  • includeScore:是否在结果中包含匹配分数(调试用),默认 false
  • includeMathces:是否返回匹配位置(高亮用),默认 false
  • minMatchCharLength:最少输入几个字符才开始搜索,默认 1 个字符就开始搜索
  • shouldSort:是否按匹配度排序结果,默认 true
  • findAllMatches:是否查找所有匹配,而不是只找第一个,默认 false
  • keys:自定义搜索字段,如果没有自定义的话,默认就是上面提到的 ['title', 'permalink', 'summary', 'content']
  • location:匹配的起始位置(配合 distance 选项使用),默认是 0
  • threshold/distance/ignoreLocation:上面提到过了,这里不再赘述

这种设计方式,可以让用户在 hugo.toml 站点的配置文件修改,就能调优搜索体验,而无需修改 JS 代码,很方便

最后,这里再额外补充下 findAllMatches 选项,这里默认 false 不是代表只返回一个搜索结果,这个选项和返回多少文档没有关系,findAllMatches 表示的是在单个字段内,是否查找多个匹配位置,而不是控制返回多少篇文章(搜索结果) ,搜索结果数量由 fuse.search(query, { limit: N }) 决定,与 findAllMatches 无关

举个例子,假设由一篇文章

javascript 复制代码
{
  title: "SSH tunnel and reverse tunnel guide",
  content: "Learn how to set up SSH tunnel. Tunnel is powerful."
}

里面有很多 tunnel 关键词,此时用户搜索 tunnel 这个关键词,有两种情况

  • findAllMatches: false:默认选项,此时 Fuse.js 在 title 字段中找到第一个 tunnel 就停止,在 content 字段中也只记录第一个匹配位置,但整篇文章仍然被作为搜索结果返回(匹配度够高)
  • findAllMatches: true:此时 Fuse.js 会找出 title 中所有 tunnel 的位置,同样也会找出 content 中所有匹配的位置,返回的文章数量不变,但每篇文章的 matches 数组里会有多个匹配项

这个功能主要用于前端高亮显示,如果想把文章中所有匹配词都标红,就把 findAllMatches 设置为 true


OK,本篇先到这里,如有疑问,欢迎评论区留言讨论,祝各位功力大涨,技术更上一层楼!!!更多内容见下篇 blog
【Ubuntu】【Hugo】搭建私人博客:搜索引擎

相关推荐
艾莉丝努力练剑2 小时前
【优选算法必刷100题】第007~008题(双指针算法):三数之和、四数之和问题求解
linux·算法·双指针·优选算法
chinesegf3 小时前
Ubuntu 安装 Python 虚拟环境:常见问题与解决指南
linux·python·ubuntu
crownyouyou3 小时前
Ubuntu输入法使用回车键后字符间距异常的问题
linux·运维·ubuntu
济6173 小时前
linux 系统移植(第十七期)---Linux 内核移植(5)-- 修改网络驱动(2)--- Ubuntu20.04
linux·运维·网络
街灯L4 小时前
【kylin-Linux】Flash兼容插件包安装
大数据·linux·运维·kylin
Howrun7775 小时前
Linux_C++网络编程四种CS模型
linux·运维·服务器
vortex55 小时前
如何快速删除 Linux 中的海量小文件:告别rm命令的缓慢困境
linux·运维·服务器
henujolly5 小时前
ethers.js读取合约信息
开发语言·javascript·区块链