smart-search · 智能搜索插件
该插件为安知鱼内容管理平台提供站内搜索功能,支持索引文章标题、正文、标签、分类、摘要与评论,并可选叠加向量语义检索。插件由白夜维护,项目主页为https://blog.byer.ink/。插件类型为searcher(替代内置搜索器)+ eventhook(订阅文章与评论事件),版本为1.1.2,要求宿主版本≥1.9.0。插件搜索结果包含文章、文档与评论三类,不监听端口、不注册路由,通过宿主的搜索接口返回。功能特性包括全文检索、评论搜索、数据库直连或HTTP公开接口兜底、打分机制、向量检索等。插件支持索引快照落盘,重启后恢复再后台重建,并提供定时全量重建、文章增量与评论事件防抖重建。数据源支持数据库直连和HTTP公开接口,插件对数据库只读,共四层只读保护。环境要求包括App版本≥1.9.0,数据库支持PostgreSQL、MySQL、SQLite之一,向量检索可选。安装过程简单,多数情况无需填写配置。配置参数丰富,支持自定义数据库连接、索引快照目录、向量检索设置等。检索行为包括分词、打分与排序、结果类型等。向量检索需满足特定条件,并支持配置和过滤门槛。索引与调度独立,支持词法索引和向量索引。前端接入无需改动主题,宿主将检索结果直接返回给前台搜索框。安全说明强调数据库只读,插件不写入、不修改宿主数据。故障排查和常见问题解答提供了解决常见问题的方法。
本插件为安知鱼(Anheyu)内容管理平台提供站内搜索:索引文章标题、正文(Markdown 与 HTML 双源)、标签、分类、摘要与评论,可选叠加向量语义检索。
维护者:白夜
插件类型:
searcher(替代内置搜索器)+eventhook(订阅文章与评论事件)插件版本:
1.1.2(要求宿主 ≥1.9.0)
1. 概述
启用后由宿主自动切换到本插件,搜索框可检索正文与评论,结果同时包含文章、文档与评论三类。
插件不监听端口、不注册路由,全部结果通过宿主的搜索接口返回,前台搜索框无需改动即可生效。
2. 功能特性
分类 | 能力 |
|---|---|
全文检索 | 标题、正文、标签、分类、摘要、关键词 |
正文双源 |
|
评论可搜 | 评论作为独立文档类型,结果带评论锚点跳转 |
数据源 | 数据库直连(默认)/ HTTP 公开接口兜底 |
打分 | 覆盖率 + IDF 加权 + 字段权重 + 短语加成 |
向量检索 | 语义召回,与词法结果按排名融合(可选,默认关闭) |
持久化 | 索引快照落盘,重启先恢复再后台重建 |
调度 | 定时全量重建 + 文章增量 + 评论事件防抖重建 |
3. 数据源
3.1 数据库直连
插件是主程序的子进程,进程环境与主程序一致,因此自动继承数据库配置,通常无需填写任何连接信息。
自动读取的变量:
PLAINTEXT
ANHEYU_DATABASE_TYPE -> postgres / mysql / sqlite
ANHEYU_DATABASE_HOST
ANHEYU_DATABASE_PORT
ANHEYU_DATABASE_USER
ANHEYU_DATABASE_PASSWORD
ANHEYU_DATABASE_NAME
sqlite 模式下主程序以 ./data/<name> 相对自身工作目录打开数据库,插件会按候选目录逐个探测真实文件,无需填写绝对路径。
无法检测到数据库配置时自动回退到 HTTP 模式,插件仍可正常启动。
3.2 HTTP 兜底
未检测到数据库配置,或开启了 db_disabled 时使用:
用途 | 接口 |
|---|---|
文章列表 |
|
文章详情 |
|
评论列表 |
|
列表接口不返回正文,插件对每篇并发拉取详情补齐(默认 8 路并发),正文为空的文章跳过详情请求。
3.3 可见性过滤
数据库模式下的过滤条件与宿主的公开可见性一致。
文章:
SQL
WHERE deleted_at IS NULL
AND status = 'PUBLISHED'
AND is_takedown = FALSE
AND review_status IN ('APPROVED','NONE')
评论:
SQL
WHERE deleted_at IS NULL
AND status = 1
草稿、待审、下架内容不会进入索引。
3.4 只读保护
插件对数据库只读,共四层:
层级 | 机制 |
|---|---|
语句白名单 | 所有查询经唯一入口,只放行 |
连接级只读 | PostgreSQL 在 DSN 附加 |
启动自检 | PostgreSQL 查询 |
只读账号(建议) | 额外配置数据库账号权限,见下方 SQL |
PostgreSQL:
SQL
CREATE ROLE anheyu_search WITH LOGIN PASSWORD '换成你的强密码';
GRANT CONNECT ON DATABASE anheyu TO anheyu_search;
GRANT USAGE ON SCHEMA public TO anheyu_search;
GRANT SELECT ON ALL TABLES IN SCHEMA public TO anheyu_search;
ALTER DEFAULT PRIVILEGES IN SCHEMA public GRANT SELECT ON TABLES TO anheyu_search;
MySQL:
SQL
CREATE USER 'anheyu_search'@'%' IDENTIFIED BY '换成你的强密码';
GRANT SELECT ON anheyu.* TO 'anheyu_search'@'%';
FLUSH PRIVILEGES;
自定义
db_dsn时,只读参数强制注入仅对 PostgreSQL 生效;MySQL 的只读设置在连接建立后执行。语句白名单对两种数据库始终生效。
4. 环境要求
项目 | 要求 |
|---|---|
App 版本 | ≥ |
数据库 | PostgreSQL / MySQL / SQLite 之一,可继承主程序配置 |
向量检索(可选) | 宿主为 PRO 版,存在 |
网络 | HTTP 兜底模式需插件进程可达 |
5. 安装
构建或获取安装包:
BASH
cd plugins/smart-search
./build.sh # 产出 smart-search.zip
后台进入「插件管理」,上传
smart-search.zip。启用插件,日志出现以下两行即为正常:
PLAINTEXT
[smart-search] 已连接数据库(postgres),只读模式,将直连读取文章与评论
[smart-search] 索引重建完成:N 条文档,来源 database,耗时 Xms
6. 快速开始
安装并启用插件,多数情况无需填写配置。
建议把
db_user/db_pass覆盖为只读账号,其余db_*留空。等待一次重建完成(默认 30 分钟一轮,重启插件可立即触发)。
前台搜索框验证:搜一个只出现在正文里的词、一个只出现在评论里的词。
7. 配置参数参考
plugin.json 的 config_schema 声明 29 项,另有 2 项由 config.go 读取但未在 manifest 中声明(article_page_size、admin_token),下表共 31 项。
数据库相关的 db_* 全部为可选覆盖,留空即继承主程序配置。
参数 | 类型 | 默认值 | 说明 |
|---|---|---|---|
| boolean |
| 打开则强制不连数据库,走 HTTP 兜底。 |
| select | 空 | 覆盖数据库类型: |
| string | 空 | 覆盖数据库主机。留空继承。 |
| number | 空 | 覆盖数据库端口。留空继承。 |
| string | 空 | 覆盖数据库用户名,建议填只读账号。留空继承。 |
| string | 空 | 覆盖数据库密码。留空继承。 |
| string | 空 | 覆盖数据库名;sqlite 模式下为数据库文件名。留空继承。 |
| string | 空 | 自定义连接串,填写后忽略上述主机/端口/用户/密码/库名。 |
| string |
| HTTP 兜底模式下的后端地址。 |
| number |
| 全量重建周期(分钟), |
| boolean |
| 是否索引评论。关闭后只索引文章。 |
| number |
| 最小词条覆盖率(0.05–1.0)。调低召回更多,调高更精准。 |
| number |
| 单次结果上限(1–500)。当前检索路径未使用,截断由宿主传入的分页大小决定。 |
| number |
| HTTP 模式下最多抓取的评论页数(每页 100 条)。 |
| number |
| HTTP 模式下文章列表每页条数(1–200)。 |
| number |
| 单次 HTTP 请求或数据库查询超时(1–120 秒)。 |
| string | 空 | HTTP 模式下为需要鉴权的后端接口预置 Token。 |
| string | 空 | 索引快照目录。留空自动使用插件安装目录之外的 |
| boolean |
| 是否启用向量语义检索。 |
| select | 空 | embedding 服务商,留空继承宿主「AI 助手」设置。 |
| string | 空 | embedding 模型,留空继承。更换模型后需重建向量索引。 |
| string | 空 | embedding API Key,留空继承。 |
| string | 空 | OpenAI 兼容接口地址(不含 |
| number |
| 融合时向量列表的权重(0–5),词法固定为 |
| number |
| 向量维度, |
| number |
| 余弦相似度绝对门槛(0–1),低于此值丢弃。 |
| number |
| 相对门槛,只保留不低于本次最高分此比例的结果(0=关闭)。 |
| number |
| 向量侧最多贡献的文档数(0=不限)。 |
| boolean |
| 是否索引宿主的 builtin 知识文档(无对应文章,命中后不可跳转)。 |
| number |
| 向量索引重建周期(小时), |
| boolean |
| 打开后每次搜索打印向量召回的原始分数,用于调参。 |
8. 检索行为
8.1 分词
文本类型 | 切分方式 | 权重类别 |
|---|---|---|
中文 | 每个单字 | weak |
中文 | 每对相邻双字 | strong |
英文 / 数字 / 标识符 | 整词 | strong |
含 | 额外按这些字符切出子词(长度 ≥ 2) | strong |
查询串中单个 ASCII 字符会被丢弃。中文覆盖基本区、扩展 A 与兼容表意区。
8.2 打分与排序
规则 | 取值 |
|---|---|
覆盖率 | 命中的 strong 词条数 ÷ 查询的 strong 词条数;查询只含单字时改用 weak |
门槛 | 覆盖率低于 |
IDF | 仅参与排序权重,不参与门槛判定 |
字段权重 | 标题 |
短语加成 | 整串查询原样出现,分数 ×2.5 |
标题加成 | 标题命中时分数 ×1.15 |
排序 | 分数降序 → 发布时间降序 → ID 升序 |
摘要围绕首个命中词取 70 字符半径,正文参与索引的上限为 20000 字符。
8.3 结果类型
| 含义 |
|
|---|---|---|
| 文章 |
|
| 文档 |
|
| 评论 | 所在页面 + |
搜索结果字段:
字段 | 说明 |
|---|---|
| 文档 ID,形如 |
| 标题;评论为「昵称 评论于 文章标题」 |
| 摘要,围绕首个命中词截取 |
|
|
| 跳转地址 |
| 标签数组 |
| 作者 |
| 主分类 |
| 发布时间 |
| 封面图 |
评论结果依赖主题版 SearchModal 识别 comment 类型。主题版本较旧时会回退显示为「文章」标签,跳转仍正常。
9. 向量检索
9.1 启用条件
条件 | 说明 |
|---|---|
| 需显式设为 |
宿主版本 | PRO 版,存在 |
数据源 | 必须直连数据库;HTTP 模式读不到这两张表,插件会跳过并记一行提示 |
embedding | 宿主「AI 助手」已配置,或在插件配置中填写 |
不满足条件时自动退回纯词法检索,不影响搜索可用性。
9.2 配置
全部可留空,自动继承宿主的 ai_assistant.embedding_*。
参数 | 默认值 | 说明 |
|---|---|---|
| 空 |
|
| 空 | 如 |
| 空 | 通常无需填写 |
| 空 | 自建网关时填写 |
|
| 融合权重 |
|
| 自动探测 |
|
| 绝对门槛 |
|
| 相对门槛 |
|
| 文档数上限 |
|
| 是否索引 builtin 知识文档 |
|
| 重建周期 |
|
| 打印召回分数 |
9.3 过滤门槛
向量命中按三层依次过滤:
顺序 | 参数 | 默认值 | 作用 |
|---|---|---|---|
1 |
|
| 绝对门槛,粗筛 |
2 |
|
| 相对门槛,只保留不低于本次最高分 85% 的结果,主要过滤手段 |
3 |
|
| 按文档计的数量上限,避免同一篇文章占满结果 |
vector_debug 打开后,日志会打印本次查询的召回数量、最佳分数与过滤后的数量,据此调整门槛。该开关会记录查询内容,调参后请关闭。
9.4 索引维护
项目 | 说明 |
|---|---|
调度 | 与词法索引分开,独立周期 |
周期 | 默认 24 小时( |
触发重建 | 重启插件可立即重建 |
宿主「重建搜索索引」 | 只清词法索引,不动向量索引 |
更换 embedding 模型 | 必须重建向量索引 |
10. 索引与调度
索引 | 周期 | 配置项 | 触发方式 |
|---|---|---|---|
词法 |
|
| 定时全量重建、文章增量、评论事件防抖 10 秒 |
向量 |
|
| 定时重建、索引缺失、重启插件 |
启动时先加载落盘快照,可立即可搜,随后在后台执行一次全量重建。
全量重建先在独立切片中收集全部文档,成功后整体替换索引,重建期间搜索结果保持可用。
快照写入采用「临时文件 + 重命名」的原子替换,目录权限 0750,并清理上次异常退出遗留的临时文件。
11. 前端接入
无需改动主题即可使用,宿主会把插件的检索结果直接返回给前台搜索框。
若需要自定义展示,按下表取字段:
字段 | 用途 |
|---|---|
| 决定结果标签与图标; |
| 结果标题 |
| 结果摘要 |
| 点击跳转地址,评论结果带 |
| 标签展示 |
| 作者与主分类 |
| 发布时间 |
| 缩略图 |
12. 安全说明
数据库只读共四层,见 §3.4;任何写语句都无法到达数据库。
插件不写入、不修改宿主数据,索引仅存在插件自身进程内存与快照文件中。
快照目录权限
0750,文件写入采用原子替换。建议额外配置只读数据库账号,见 §3.4 的建号 SQL。
13. 故障排查
现象 | 可能原因 | 处理 |
|---|---|---|
只能搜到标题,搜不到正文 | 数据库模式未生效,回退到 HTTP 且详情拉取失败 | 检查日志是否有「已连接数据库…只读模式」;确认 |
搜不到评论 |
| 开启 |
索引一直是 0 条 | 数据库连接失败且 HTTP 兜底也不可达 | 查看启动日志的连接错误;核对 |
向量检索没生效 |
| 查看日志提示,逐项核对 §9.1 |
日志报 | 旧版本曾把只读会话写进 MySQL DSN | 升级到当前版本 |
sqlite 找不到文件 | 主程序数据文件不在候选目录中 | 用 |
14. 常见问题
Q:需要配置数据库连接吗? A:通常不需要。插件是宿主子进程,自动继承 ANHEYU_DATABASE_*。
Q:能同时搜文章和评论吗? A:能。评论作为独立文档类型索引,结果带锚点跳转。关闭 include_comments 后只返回文章。
Q:向量检索要额外付费吗? A:向量化会调用 embedding 接口,按宿主的服务商计费。索引重建周期默认 24 小时,避免频繁消耗额度。
Q:更换 embedding 模型后要做什么? A:重建向量索引。模型不同则维度与语义空间不同,旧向量不可复用。
Q:新文章要等多久才能搜到? A:宿主推送文章后即时增量生效。若宿主未推送正文,则等下一次全量重建(默认 30 分钟)。
Q:评论删除后还会出现在结果里吗? A:数据库模式下会在下一次全量重建时清理。
15. 限制与已知事项
文章事件负载不含正文,增量索引依赖宿主随后调用
IndexArticle;未调用时需等下一次全量重建。评论删除与审核变更不触发事件,实时性受
rebuild_interval_min约束。依赖
articles/comments/article_post_tags/article_post_categories四张表的字段名,宿主大版本改动字段时需同步更新插件。max_results当前未被检索路径使用,实际截断由宿主传入的分页大小决定。向量检索必须直连数据库,HTTP 模式下不可用。