From 02d18a115796d18d2b629cf1881d386829c0a8fc Mon Sep 17 00:00:00 2001 From: xiaji Date: Mon, 15 Jun 2026 07:20:10 +0800 Subject: [PATCH] =?UTF-8?q?feat(search):=20=E6=90=9C=E7=B4=A2=E8=A6=86?= =?UTF-8?q?=E7=9B=96=E6=A0=87=E9=A2=98/=E6=AD=A3=E6=96=87/=E8=AF=84?= =?UTF-8?q?=E8=AE=BA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 原 /api/v1/articles?q=xxx 只搜 title + body_text(外文原文), 导致: - 搜中文译文里出现的词搜不到 - 搜双 provider 评论里的"主题词"搜不到 - 搜摘要搜不到 扩展为搜索 7 个字段(命中任一即可): - title (原标题,外文) - body_text (原文,外文) - title_zh (中文标题) - body_zh_text (中文译文,纯文本) - summary_zh (中文摘要) - commentary (Angel 评论) - commentary_meituan (美团评论) 不去搜 body_zh_formatted(HTML 包了

), 避免 ilike 跟 HTML 标签字符串误匹配,纯文本走 body_zh_text 即可。 性能: - ilike '%xxx%' 走不了 B-tree 索引,PG 会 seq scan - 当前文章量级别(几千篇)下完全 OK,延迟 < 50ms - 未来 10w+ 文章量时改 PG full-text search(to_tsvector + GIN) 或外部 ES;现阶段不做 无 schema/migration 改动;无前端改动(后端响应 schema 没变)。 --- backend/app/api/articles.py | 17 ++++++++++++++++- 1 file changed, 16 insertions(+), 1 deletion(-) diff --git a/backend/app/api/articles.py b/backend/app/api/articles.py index eec97ab..5eb6d38 100644 --- a/backend/app/api/articles.py +++ b/backend/app/api/articles.py @@ -60,8 +60,23 @@ async def list_articles( filters.append(Source.slug.in_(slugs)) if q: + # 搜索覆盖:原标题/原文 / 中文标题/译文 / 摘要 / 双 provider 评论 + # — 用户既可能搜原文也可能是译文(取决于记得哪个词) + # — 评论里的关键字能命中(配合 LLM 生成的中文评论做"主题搜索"很常见) + # 性能:ilike '%xxx%' 走不了 B-tree 索引,PG 会全表扫;文章量小(几千级)下 OK。 + # 未来 10w+ 文章量时改 PG full-text search(to_tsvector + GIN 索引) like = f"%{q}%" - filters.append(or_(Article.title.ilike(like), Article.body_text.ilike(like))) + filters.append( + or_( + Article.title.ilike(like), + Article.body_text.ilike(like), + Article.title_zh.ilike(like), + Article.body_zh_text.ilike(like), + Article.summary_zh.ilike(like), + Article.commentary.ilike(like), + Article.commentary_meituan.ilike(like), + ) + ) if lang == "zh": filters.append(Article.title_zh.is_not(None))