5.1 KiB
5.1 KiB
规则过滤引擎设计
1. 目标
当前过滤层的定位是:
- 不让 LLM 直接做最终过滤决策
- 让 LLM 只产出结构化信号
- 由规则引擎输出最终
keep / drop / review决策
当前链路是:
item -> content extraction -> llm summary -> filter rule engine
2. 输入输出
2.1 FilterInput
过滤层统一读取四类输入:
itemarticlesummarycontext
其中:
item表示上游标准化候选条目article表示正文提取结果summary表示结构化 LLM 摘要结果context表示额外的用户偏好或运行时上下文
2.2 FilterDecisionResult
过滤结果统一输出:
decisionkeepdropreview
matched_rulesreasonslabelsprioritymatches
这样后续的知识库 sink、推送层或人工审核都可以稳定消费。
3. 规则结构
当前规则文件位置:
configs/filter_rules.json
单条规则结构为:
{
"rule_id": "keep-worth-keeping-method",
"enabled": true,
"stop_on_match": false,
"conditions_all": [
{ "field": "summary.worth_keeping", "op": "eq", "value": true },
{ "field": "summary.category", "op": "in", "value": ["方法论", "工具实践"] }
],
"action": {
"decision": "keep",
"reason": "Structured summary marked the content as worth keeping in a durable category.",
"labels": ["summary", "durable"],
"priority": 80
}
}
4. 当前支持的操作符
eqneinnot_incontainsoverlapgtelteexists
当前条件组合方式:
conditions_allconditions_any
5. 动态上下文字段
规则支持从其他字段动态取值,例如:
{ "field": "summary.topics", "op": "overlap", "value": { "from_field": "context.interest_topics" } }
这允许上层 Agent 在调用 filter_summary_result 时,把当前关注主题动态注入,而不必把偏好硬编码在规则文件里。
6. 当前默认规则思路
当前默认规则分为三类:
- 质量拦截
- 低质量正文直接
drop - 疑似截断或付费墙进入
review
- 低质量正文直接
- 摘要价值判断
资讯 + worth_keeping=false直接drop方法论/工具实践 + worth_keeping=true直接keep
- 个性化补充信号
summary.topics与context.interest_topics重叠时提升为keep- 其他
worth_keeping=true的结果默认进入review
7. 规则执行流程
当前过滤流程按以下顺序执行:
- 上层先产出结构化
summary - 可选附带
item、article与context - 规则引擎按
priority从高到低遍历规则 - 每条规则根据
conditions_all/conditions_any判断是否命中 - 命中的规则被收集为
matches - 最终根据命中结果收敛为
keep / drop / review
当前决策收敛规则是:
- 只要命中任意
drop,最终结果就是drop - 否则只要命中任意
keep,最终结果就是keep - 否则如果命中任意
review,最终结果就是review - 如果没有任何规则命中,默认回落到
review
这样设计的原因是:
drop应该拥有最高约束力keep只在没有硬性淘汰时生效- 默认不自动放行未知内容
8. 为什么让 LLM 调用规则 tool,而不是直接裁决
当前架构故意拆成两层:
- LLM 负责生成结构化信号
- 规则引擎负责输出最终过滤决策
原因是:
- LLM 适合做语义理解、归类、摘要和价值信号提取
- 规则引擎适合做稳定、可复现、可审计的最终判断
因此推荐的调用方式是:
- LLM 先调用提取 tool
- LLM 或本地脚本产出
summary_result - LLM 再调用
filter_summary_result - 后续根据过滤结果决定是否入库、推送或人工审核
这意味着:
- LLM 是编排者
- rule engine 是裁决器
而不是让 LLM 在过滤阶段再次自由发挥。
9. 调用示例
9.1 本地脚本
python scripts/run_filter_rules.py ^
--summary outputs/reference/summary/result.loop.json ^
--extracted outputs/reference/extracted/read-flow-2026.extracted.json ^
--output outputs/reference/filter/filter-decision.json
9.2 带上下文的调用
{
"interest_topics": ["个人信息管理", "阅读工作流"]
}
将这份上下文作为 --context 传入后,规则就可以根据当前关注主题做加权。
9.3 MCP tool
filter_summary_result 接收:
summary_result- 可选
extracted_article - 可选
item - 可选
context
返回:
decisionmatched_rulesreasonslabelsprioritymatches
10. 当前落地位置
- 过滤模型:
src/summary_mcp/models/filtering.py
- 规则引擎:
src/summary_mcp/filters/engine.py
- 默认规则:
configs/filter_rules.json
- 本地运行脚本:
scripts/run_filter_rules.py
- MCP tool:
filter_summary_result
11. 当前阶段的设计结论
第一版过滤层采用“规则主导,LLM 提供信号”的架构:
- LLM 不直接做最终裁决
- 上层 Agent 可以决定是否调用过滤 tool
- 真正的过滤决策由规则引擎输出
- 灰区内容后续再考虑是否引入第二层 LLM 辅助判断