富文本检索通常需要搜索正文而不是标签。先区分两个目标:只让索引分析忽略 HTML,还是实际生成一份纯文本字段。前者可交给分析器,后者需在采集或应用层建立投影;它们都不等于网页安全清洗。

旧 Logstash 规则的作用和限制

原来的做法是用 mutate/gsub 删除像标签的片段、制表符和  。如果还要保留原文,至少先复制到新字段:

filter {
  mutate {
    copy => { "content" => "search_text" }
  }
  mutate {
    gsub => [
      "search_text", "<.*?>|\\t|&nbsp;", ""
    ]
  }
}

这是旧规则的有限用途,不是可靠的 HTML 转纯文本算法。标签可能跨行,属性中可能有大于号,还存在各种实体;删除标签也会把相邻段落拼在一起。复杂 HTML 应使用解析器,并明确段落空格、脚本、样式和实体的处理规则。Logstash mutate 插件

只影响检索分析,可以用 html_strip

Elasticsearch 7.3 的 html_strip 字符过滤器会去掉 HTML 元素并解码实体。下面展示只读分析请求的路径和请求体:

POST _analyze
{
  "char_filter": ["html_strip"],
  "tokenizer": "standard",
  "text": "<p>hello <b>world</b> &amp; search</p>"
}

中文检索还需使用实际字段的分析链。配置字符过滤器只改变分析过程,不会自动把 _source 里的 HTML 改写为纯文本。Elasticsearch 7.3 html_strip

原文、搜索投影和展示各司其职

可以保留 content_html,另建 search_text 用于检索、摘要或导出。规则变动后应能够从原文重新生成投影,避免永久丢失信息;缺失值、空串、段落边界也要有一致约定。

去标签不等于 XSS 防护。富文本回到网页前仍需按展示场景净化与转义,搜索片段也不能直接当作可信 HTML。是否独立存纯文本,取决于是否需要返回或导出它,而不只是关键词能不能命中。