Refine OpenClaw payloads and reorganize docs

This commit is contained in:
zhuyongxin
2026-03-26 10:20:07 +08:00
parent cecf4d3ae7
commit 27fe1e8882
155 changed files with 8999 additions and 87 deletions
+3 -1
View File
@@ -1,4 +1,6 @@
.claude/
.claude/
.codex/
__pycache__/
*.pyc
.env.local
+49 -20
View File
@@ -1,4 +1,4 @@
# Content Extract MCP
# Content Extract MCP
Python MCP scaffold for article content extraction, structured summary validation, deterministic filtering, and Markdown sink output.
@@ -18,16 +18,16 @@ The server exposes three tools:
Validate an LLM summary result:
```bash
validate-llm-result outputs/result.json --extracted outputs/read-flow-2026.extracted.json
validate-llm-result outputs/reference/summary/result.json --extracted outputs/reference/extracted/read-flow-2026.extracted.json
```
Run the minimal extraction-to-summary loop:
```bash
python scripts/run_summary_loop.py ^
--extracted outputs/read-flow-2026.extracted.json ^
--prompt outputs/llm-summary-prompt.txt ^
--output outputs/result.json
--extracted outputs/reference/extracted/read-flow-2026.extracted.json ^
--prompt outputs/prompts/llm-summary-prompt.txt ^
--output outputs/reference/summary/result.loop.json
```
Pull FreshRSS entries and map them into normalized `item` objects:
@@ -41,8 +41,8 @@ python scripts/pull_freshrss_items.py --limit 5
The script writes:
- `outputs/freshrss.raw.json`
- `outputs/freshrss.items.json`
- `outputs/freshrss/raw/freshrss.raw.json`
- `outputs/freshrss/items/freshrss.items.json`
Pull FreshRSS entries and run content extraction for each mapped item:
@@ -55,37 +55,66 @@ python scripts/run_freshrss_extract.py --limit 1
The script writes:
- `outputs/freshrss.raw.json`
- `outputs/freshrss.items.json`
- `outputs/freshrss.extracted.json`
- `outputs/freshrss/raw/freshrss.raw.json`
- `outputs/freshrss/items/freshrss.items.json`
- `outputs/freshrss/extracted/freshrss.extracted.json`
Run deterministic filter rules against a structured summary result:
```bash
python scripts/run_filter_rules.py ^
--summary outputs/result.json ^
--extracted outputs/read-flow-2026.extracted.json ^
--output outputs/filter-decision.json
--summary outputs/reference/summary/result.loop.json ^
--extracted outputs/reference/extracted/read-flow-2026.extracted.json ^
--output outputs/reference/filter/filter-decision.json
```
You can optionally pass a context file to inject interest topics or source tags:
```bash
python scripts/run_filter_rules.py ^
--summary outputs/result.json ^
--extracted outputs/read-flow-2026.extracted.json ^
--context outputs/filter-context.json ^
--output outputs/filter-decision.with-context.json
--summary outputs/reference/summary/result.loop.json ^
--extracted outputs/reference/extracted/read-flow-2026.extracted.json ^
--context outputs/reference/filter/filter-context.json ^
--output outputs/reference/filter/filter-decision.with-context.json
```
Write a filtered result into the Markdown sink:
```bash
python scripts/run_markdown_sink.py ^
--summary outputs/result.json ^
--extracted outputs/read-flow-2026.extracted.json ^
--filter outputs/filter-decision.json
--summary outputs/reference/summary/result.loop.json ^
--extracted outputs/reference/extracted/read-flow-2026.extracted.json ^
--filter outputs/reference/filter/filter-decision.json
```
The script writes markdown notes under `knowledge-base/`.
Build an internal `ArticleCandidateRecord` and a slim `OpenClawCandidateInput`:
```bash
python scripts/run_article_candidate.py ^
--summary outputs/reference/summary/result.loop.json ^
--extracted outputs/reference/extracted/read-flow-2026.extracted.json ^
--filter outputs/reference/filter/filter-decision.json ^
--section-hint tools_and_workflows
```
The script writes by default:
- `outputs/reference/candidates/article-candidate-record.json`
- `outputs/reference/candidates/openclaw-candidate-input.json`
Build a batch OpenClaw delivery payload:
```bash
python scripts/build_openclaw_delivery.py ^
--input-dir outputs/freshrss/candidates/batch ^
--sort-by-rank ^
--date 2026-03-25
```
The script writes by default:
- `outputs/reference/candidates/openclaw-delivery-payload.json`
Output layout details live in `outputs/README.md`.
+29 -10
View File
@@ -1,8 +1,8 @@
# TODO
# TODO
## 当前状态
项目当前处于 `Content Extract MCP` 的 MVP 完成,已进入规则过滤与 Markdown sink 阶段。
项目当前处于 `Content Extract MCP` 的 MVP 完成阶段,已验证 `规则过滤 + Markdown sink`,下一阶段将转向 `OpenClaw 日报聚合 + 知识沉淀` 改造。
已完成:
@@ -25,6 +25,8 @@
- [x] 实现第一版规则引擎与过滤 MCP tool
- [x] 定义 sink 输入输出 schema
- [x] 实现第一版 Markdown sink 与本地写入脚本
- [x] 明确下一阶段主路径应调整为 `候选材料 -> 日报 -> 人工确认 -> 知识沉淀`
- [x] 明确 `ArticleCandidateRecord` 与 `OpenClawCandidateInput` 需要分层设计
---
@@ -45,14 +47,26 @@
- [x] 跑通 `FreshRSS -> item -> content extraction` 单条链路
- [x] 定义规则过滤层的输入输出 schema
- [x] 设计知识库入库格式
- [ ] 设计 webhook / 推送格式
- [x] 在文档层定义 `ArticleCandidateRecord`、`OpenClawCandidateInput` 与 `DailyDigest`
- [x] 在代码里把当前 `article_candidate` 重新定位为 `ArticleCandidateRecord`
- [x] 新增 `OpenClawCandidateInput` 模型与转换逻辑
- [x] 给 `OpenClawCandidateInput` 增加 `canonical_url` 与 `language`
- [x] 输出面向 OpenClaw 的精简 `OpenClawCandidateInput` 批量载荷
- [x] 将“人工确认状态”拆成独立模型,不回写到 candidate 输入对象
- [ ] 设计 OpenClaw webhook / delivery payload 的实际传输方式
- [ ] 设计“人工确认后再沉淀知识库”的状态流转
- [ ] 给提取结果增加更多正文清洗策略,比如尾部噪音清理
- [ ] 细化过滤规则并引入更多个性化上下文
- [ ] 收敛 `paywall` 误判规则,避免仅因正文提到“付费/收费”就进入高优先级 `review`
---
## P2 - 后续增强项
- [ ] 将当前 `Markdown sink` 调整为 debug / fallback 能力,而非主路径
- [ ] 增加按天批量收集 `ArticleCandidateRecord` 的脚本
- [ ] 让 OpenClaw 聚合候选内容并生成日报
- [ ] 将日报写入知识库,并同步生成面向用户的汇报消息
- [ ] 增加批量提取能力
- [ ] 引入 Playwright 作为动态页面兜底抓取方案
- [ ] 支持更多 `content_kind`,例如 `release`、`thread`、`video`
@@ -65,16 +79,21 @@
## 当前建议的下一步
优先做这两件事:
优先做这三件事:
1. 设计 webhook / 推送格式
2. 细化过滤规则并引入更多个性化上下文
1. 设计 OpenClaw webhook / delivery payload 的实际传输方式
2. 收敛 `paywall` 误判规则
3. 设计人工确认后进入知识库的状态流转
---
## 收束上下文后建议先看
- docs/context-reset-brief.md
- docs/filter-rule-engine-design.md
- docs/markdown-sink-design.md
- TODO.md
- docs/current/context-reset-brief.md
- docs/openclaw/openclaw-candidate-input-field-spec.md
- docs/openclaw/openclaw-delivery-payload-spec.md
- docs/openclaw/openclaw-daily-digest-refactor.md
- docs/openclaw/article-candidate-daily-digest-schema.md
- docs/design/filter-rule-engine-design.md
- docs/design/markdown-sink-design.md
- TODO.md
+57 -22
View File
@@ -1,20 +1,43 @@
# 文档索引
# 文档索引
## 当前目录结构
- `docs/README.md`
- 文档总索引
- `docs/current/`
- 当前状态、收束入口、阶段导航
- `docs/design/`
- 当前实现的设计文档
- `docs/openclaw/`
- OpenClaw 日报聚合与下游对象设计
- `docs/notes/`
- 较上层的方案笔记与非最终设计
- `docs/archive/`
- 历史归档,不作为最新事实来源
## 当前推荐阅读顺序
1. `context-reset-brief.md`
1. `docs/current/context-reset-brief.md`
- 当前真实进度与下一步入口
2. `summary-mcp-service-design.md`
2. `docs/openclaw/openclaw-candidate-input-field-spec.md`
- 提供给 OpenClaw 的单篇结构化输入字段说明
3. `docs/openclaw/openclaw-delivery-payload-spec.md`
- 提供给 OpenClaw 的批量投递 envelope 说明
4. `docs/design/summary-mcp-service-design.md`
- 当前 MCP 服务的职责、接口和边界
3. `filter-rule-engine-design.md`
5. `docs/design/filter-rule-engine-design.md`
- 过滤层的输入输出、规则结构与当前实现
4. `markdown-sink-design.md`
6. `docs/design/markdown-sink-design.md`
- 第一版 Markdown sink 的输入输出、目录结构与落地方式
5. `source-schema-design.md`
7. `docs/openclaw/openclaw-daily-digest-refactor.md`
- 为什么要从单篇入库改成 OpenClaw 日报聚合链路
8. `docs/openclaw/article-candidate-daily-digest-schema.md`
- `ArticleCandidateRecord`、`OpenClawCandidateInput` 与 `DailyDigest` 的正式设计
9. `docs/design/source-schema-design.md`
- `source -> item -> document` 的对象设计
6. `reading-pipeline-design-notes.md`
10. `docs/notes/reading-pipeline-design-notes.md`
- 更上层的阅读流方案与阶段划分
7. `summary-loop-explained.md`
11. `docs/design/summary-loop-explained.md`
- 当前 LLM 摘要校验闭环的解释
## 当前文档分层
@@ -25,39 +48,51 @@
- 仓库入口与脚本运行方式
- `TODO.md`
- 当前优先级、已完成项、下一阶段任务
- `docs/context-reset-brief.md`
- `docs/current/context-reset-brief.md`
- 当前阶段状态的最短摘要
- `docs/README.md`
- 文档索引与阅读顺序
### 2. 当前实现设计
- `docs/summary-mcp-service-design.md`
- `docs/design/summary-mcp-service-design.md`
- 当前内容提取 MCP 的真实设计
- `docs/summary-core-interface-design.md`
- `docs/design/summary-core-interface-design.md`
- 摘要/提取内核的接口抽象
- `docs/source-schema-design.md`
- `docs/design/source-schema-design.md`
- `source`、`item`、`document` 三层 schema
- `docs/summary-loop-explained.md`
- `docs/design/summary-loop-explained.md`
- 提取 JSON -> LLM 摘要 JSON -> 校验 的闭环说明
- `docs/filter-rule-engine-design.md`
- `docs/design/filter-rule-engine-design.md`
- 第一版规则过滤引擎设计与落地位置
- `docs/markdown-sink-design.md`
- `docs/design/markdown-sink-design.md`
- 第一版 Markdown sink 设计与落地位置
### 3. 上下游方案设计
### 3. OpenClaw 与下游设计
- `docs/reading-pipeline-design-notes.md`
- `docs/openclaw/openclaw-candidate-input-field-spec.md`
- 提供给 OpenClaw 的单篇结构化输入字段说明
- `docs/openclaw/openclaw-delivery-payload-spec.md`
- 提供给 OpenClaw 的批量投递 envelope 说明
- `docs/openclaw/openclaw-daily-digest-refactor.md`
- 改造为 OpenClaw 日报聚合链路的原因与目标结构
- `docs/openclaw/article-candidate-daily-digest-schema.md`
- `ArticleCandidateRecord`、`OpenClawCandidateInput` 与 `DailyDigest` 的字段设计与对象关系
### 4. 方案笔记
- `docs/notes/reading-pipeline-design-notes.md`
- 整体阅读流、规则、sink、push 的方案笔记
### 4. 历史归档
### 5. 历史归档
- `docs/content-extract-mcp-mvp-archive.md`
- `docs/archive/content-extract-mcp-mvp-archive.md`
- MVP 阶段归档,部分状态已被后续进展覆盖
## 当前文档维护原则
- `context-reset-brief.md` 记录当前最新状态
- `docs/current/context-reset-brief.md` 记录当前最新状态
- `TODO.md` 记录任务优先级与下一步
- `content-extract-mcp-mvp-archive.md` 只当历史快照,不再作为最新事实来源
- 新增阶段性进展,优先更新 `README.md`、`TODO.md`、`context-reset-brief.md`
- `outputs/README.md` 记录当前输出目录约定
- `docs/archive/content-extract-mcp-mvp-archive.md` 只当历史快照,不再作为最新事实来源
- 新增阶段性进展,优先更新 `README.md`、`TODO.md`、`docs/current/context-reset-brief.md`
@@ -1,4 +1,4 @@
# 项目当前状态简报
# 项目当前状态简报
## 当前已完成
@@ -60,11 +60,11 @@
- Markdown sink 脚本:
- `scripts/run_markdown_sink.py`
- Markdown sink 文档:
- `docs/markdown-sink-design.md`
- `docs/design/markdown-sink-design.md`
- 当前提示词:
- `outputs/llm-summary-prompt.txt`
- `outputs/prompts/llm-summary-prompt.txt`
- 过滤结果样例:
- `outputs/filter-decision.json`
- `outputs/reference/filter/filter-decision.json`
- 文档索引:
- `docs/README.md`
- 当前 TODO:
@@ -99,4 +99,4 @@
## 一句话结论
当前 MVP 已完成,FreshRSS 上游、第一版规则过滤层和第一版 Markdown sink 都已接通,下一阶段应转向推送层与更完整的下游集成。
当前 MVP 已完成,FreshRSS 上游、第一版规则过滤层和第一版 Markdown sink 都已接通,下一阶段应转向推送层与更完整的下游集成。
@@ -1,4 +1,4 @@
# 规则过滤引擎设计
# 规则过滤引擎设计
## 1. 目标
@@ -169,9 +169,9 @@
```bash
python scripts/run_filter_rules.py ^
--summary outputs/result.json ^
--extracted outputs/read-flow-2026.extracted.json ^
--output outputs/filter-decision.json
--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 带上下文的调用
@@ -1,4 +1,4 @@
# Summary Loop 工作说明
# Summary Loop 工作说明
## 1. 目的
@@ -15,7 +15,7 @@
这个闭环由三部分组成:
- 提取结果
- 来自 `outputs/*.extracted.json`
- 来自 `outputs/reference/extracted/*.json` 或 `outputs/freshrss/extracted/*.json`
- 提供标题、链接、正文、质量标记
- LLM 摘要
@@ -53,8 +53,8 @@
脚本主要使用两个输入文件:
- 提取结果:`outputs/read-flow-2026.extracted.json`
- 摘要 prompt:`outputs/llm-summary-prompt.txt`
- 提取结果:`outputs/reference/extracted/read-flow-2026.extracted.json`
- 摘要 prompt:`outputs/prompts/llm-summary-prompt.txt`
提取结果不会整包无差别塞给 LLM,而是先裁剪成更小的摘要输入:
@@ -187,16 +187,16 @@ validator
每次执行脚本都会在输出目录下留下调试痕迹:
- `result.loop.attempt-1.raw.txt`
- `outputs/reference/summary/result.loop.attempt-1.raw.txt`
- 模型原始输出
- `result.loop.attempt-1.json`
- `outputs/reference/summary/result.loop.attempt-1.json`
- 提取出的 JSON 结果
- `result.loop.attempt-1.validation.json`
- `outputs/reference/summary/result.loop.attempt-1.validation.json`
- 这一轮的校验报告
- `result.loop.json`
- `outputs/reference/summary/result.loop.json`
- 当前最终结果
这些文件的价值是:
@@ -0,0 +1,488 @@
# Article Candidate / OpenClaw Input / Daily Digest 设计
## 1. 文档目的
本文档正式定义 OpenClaw 日报链路中的三层对象:
- `ArticleCandidateRecord`
- `OpenClawCandidateInput`
- `DailyDigest`
目标不是只定义字段,而是明确每一层对象的职责边界,避免把“内部记录对象”和“发给 OpenClaw 的下游输入对象”混成同一个 payload。
---
## 2. 这次为什么要改
前一版设计里,`article_candidate` 同时承担了三种职责:
1. 本地审计与追溯
2. 规则过滤后的内部候选记录
3. 发给 OpenClaw 的下游输入
这会直接带来三个问题:
- 字段过重
- `article.plain_text` 这类正文内容会显著增加 token 消耗
- 字段过细
- `filter_decision.matches`、`matched_rules`、`labels` 这类规则证据链更适合本地审计,不适合发给下游聚合器
- 字段过耦合
- `source_refs` 是本地文件系统路径,对 OpenClaw 没有意义,反而会让上下游绑定内部实现
批量跑完 `FreshRSS -> extraction -> LLM summary -> filter -> article_candidate` 后,这个问题已经非常清楚:
- 本地对象需要尽量保留信息,便于追溯误判
- OpenClaw 输入需要尽量精简,便于聚合日报和控制 token
因此,正确改法不是继续给一个 `article_candidate` 做加减法,而是把对象拆层。
---
## 3. 设计结论
建议正式拆成三层:
### 3.1 `ArticleCandidateRecord`
定位:
- 内部候选记录对象
- 面向本地留档、审计、调试、复跑
它回答的问题是:
- 这条候选内容从哪里来
- 提取、摘要、过滤各阶段到底产出了什么
- 为什么规则引擎会给出当前决策
- 后续如果要重放或排查,该去哪里追溯
### 3.2 `OpenClawCandidateInput`
定位:
- 发给 OpenClaw 的精简输入对象
- 面向日报聚合与编排
它回答的问题是:
- 这条内容是什么
- 为什么值得放进候选池
- 应该如何排序和栏目化
它不负责保存本地调试信息,也不负责承载完整正文。
### 3.3 `DailyDigest`
定位:
- OpenClaw 聚合后的日级主产物
- 面向日报汇报、知识沉淀、人工 review
它回答的问题是:
- 今天最值得关注的内容是什么
- 这些内容能提炼出什么结论
- 哪些内容值得进入长期知识库
---
## 4. 推荐链路
推荐把链路明确为:
`item -> article -> summary -> filter_result -> ArticleCandidateRecord -> OpenClawCandidateInput -> DailyDigest`
这里有两个关键转换:
1. `summary + filter_result` 先生成 `ArticleCandidateRecord`
- 这是内部标准记录
2. `ArticleCandidateRecord` 再投影成 `OpenClawCandidateInput`
- 这是跨系统传输对象
这样做的本质是:
- 内部对象追求可追溯
- 下游对象追求低耦合、低 token、高可消费性
---
## 5. `ArticleCandidateRecord` 设计
### 5.1 角色定义
`ArticleCandidateRecord` 是当前项目内部的正式候选记录对象。
它不是:
- 发给 OpenClaw 的最终 payload
- 发给用户的日报消息
- 最终知识库对象
它是下游所有再加工动作之前的“内部事实底稿”。
### 5.2 设计原则
- 保留上游对象,便于调试和重放
- 保留规则证据链,便于解释误判
- 保留本地引用,便于审计
- 允许后续重新生成不同版本的下游 payload
### 5.3 建议字段
```json
{
"candidate_id": "cand:sha256:xxx",
"item": {"...": "Item"},
"article": {"...": "ExtractedArticle"},
"summary": {"...": "LlmSummaryResult"},
"filter_result": {"...": "FilterDecisionResult"},
"digest_section_hint": "insights",
"digest_rank": 60,
"review_state": "pending",
"rendered_markdown": null,
"metadata": {
"generated_at": "2026-03-25T10:00:00Z",
"pipeline_version": "v2",
"producer": "summary_mcp",
"run_id": "candidate-2026-03-25-001"
},
"source_refs": {
"item_path": "outputs/freshrss/items/batch/item-01.item.json",
"extracted_path": "outputs/freshrss/extracted/batch/item-01.extracted.json",
"summary_path": "outputs/freshrss/summary/batch/item-01/result.loop.json",
"filter_path": "outputs/freshrss/filter/batch/item-01.filter.json"
}
}
```
### 5.4 字段说明
- `candidate_id`
- 候选记录唯一标识
- 建议基于 `item_id` 或 `extract_id` 派生
- `item`
- 保留来源、标题、发布时间、作者等上游元数据
- `article`
- 保留正文提取结果与质量标记
- 供本地调试与重放使用
- `summary`
- 保留结构化摘要结果
- 是后续 OpenClaw 输入映射的主要来源
- `filter_result`
- 保留规则引擎的完整裁决与命中细节
- 主要用于解释和排查
- `digest_section_hint`
- 给 OpenClaw 的栏目建议
- `digest_rank`
- 给 OpenClaw 的排序信号
- `review_state`
- 记录人工复核状态
- `rendered_markdown`
- 可选的人类可读卡片
- 用于调试或 fallback 展示
- `metadata`
- 记录运行时元信息
- `source_refs`
- 仅用于本地追溯
- 不应进入跨系统 payload
### 5.5 为什么内部对象要保留正文和完整过滤结果
因为这层对象不是给 OpenClaw 直接消费的,而是给系统内部留档的。
如果这里过早裁掉字段,会丢失两种关键能力:
1. 误判排查能力
- 例如文章被误判为 `paywall` 时,必须能回看 `article` 与 `filter_result`
2. 下游重放能力
- 后面如果调整了 OpenClaw payload 或摘要策略,可以从这层重新投影,而不必重新抓取全文
---
## 6. `OpenClawCandidateInput` 设计
### 6.1 角色定义
`OpenClawCandidateInput` 是当前项目发给 OpenClaw 的正式输入对象。
它应当是:
- 扁平化的
- 精简的
- 稳定的
- 不依赖本地文件路径的
### 6.2 设计原则
- 不携带正文全文
- 不携带规则引擎的完整证据链
- 不携带本地 `source_refs`
- 只保留 OpenClaw 聚合日报真正需要的字段
### 6.3 建议字段
```json
{
"candidate_id": "cand:sha256:xxx",
"title": "套壳中国大模型撑起500亿美元估值?扒一扒 Cursor 的套壳疑云",
"url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"published_at": "2026-03-21T10:19:11Z",
"author": "阮一峰",
"source_name": "阮一峰博客",
"summary": "2 到 3 句话摘要",
"highlights": ["...", "...", "..."],
"keywords": ["Cursor", "Kimi K2.5"],
"topics": ["人工智能", "商业伦理"],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "有持续性的行业洞察价值",
"selection_decision": "review",
"selection_reason": "worth_keeping=true but no stronger keep rule matched",
"digest_section_hint": "insights",
"digest_rank": 60
}
```
### 6.4 字段说明
- `candidate_id`
- 与内部记录保持同一主键,便于回溯
- `title` / `url` / `published_at` / `author` / `source_name`
- OpenClaw 做日报聚合所需的最小来源信息
- `summary` / `highlights` / `keywords` / `topics` / `category`
- OpenClaw 聚合时真正需要的语义材料
- `worth_keeping` / `worth_reason`
- 摘要层提供的长期价值判断信号
- `selection_decision` / `selection_reason`
- 规则层的压缩结果
- 用于告诉 OpenClaw:这条为什么进入候选池,以及应该怎样对待
- `digest_section_hint` / `digest_rank`
- OpenClaw 做栏目化和排序时最直接的信号
### 6.5 为什么不用正文全文
因为 OpenClaw 当前承担的是“日报聚合”角色,不是“再次全文阅读器”。
如果把 `article.plain_text` 一并发给 OpenClaw,会出现三个问题:
1. token 浪费
- 每条都携带全文,批量聚合时成本会迅速膨胀
2. 角色混乱
- OpenClaw 会被迫重新阅读原文,而不是消费上游已经压缩好的摘要结果
3. 输入不稳定
- 正文长度差异很大,会让聚合阶段的上下文更难控制
因此,正文应保留在 `ArticleCandidateRecord`,而不是进入 `OpenClawCandidateInput`。
### 6.6 为什么过滤结果要压缩
完整的 `filter_result` 适合本地审计,不适合跨系统传输。
OpenClaw 通常只需要知道:
- 这条是 `keep / review / drop` 中的哪一种
- 为什么会进入候选池
- 优先级大概是多少
它通常不需要知道:
- 具体命中了哪几条规则
- 每条规则携带了哪些 labels
- 完整的 `matches` 证据链
所以建议把规则层压缩为:
- `selection_decision`
- `selection_reason`
- `digest_rank`
### 6.7 为什么不要 `source_refs`
因为 `source_refs` 是本地实现细节,不是业务语义。
把它发给 OpenClaw 的问题有两个:
1. 没价值
- OpenClaw 无法消费本地磁盘路径
2. 高耦合
- 这会让 OpenClaw 输入隐式依赖当前项目的目录结构与输出命名方式
因此,`source_refs` 应只保留在 `ArticleCandidateRecord`。
---
## 7. 两个对象之间的映射关系
建议映射规则如下:
- `OpenClawCandidateInput.candidate_id`
- 来自 `ArticleCandidateRecord.candidate_id`
- `title` / `url` / `published_at` / `author`
- 优先来自 `item`
- `source_name`
- 优先来自 `item.source_title`,没有时可退化为域名或作者来源
- `summary` / `highlights` / `keywords` / `topics` / `category`
- 来自 `summary`
- `worth_keeping` / `worth_reason`
- 来自 `summary.worth_keeping` 与 `summary.reason`
- `selection_decision`
- 来自 `filter_result.decision`
- `selection_reason`
- 可取 `filter_result.reasons[0]` 或压缩后的组合说明
- `digest_section_hint`
- 来自 `ArticleCandidateRecord.digest_section_hint`
- `digest_rank`
- 来自 `ArticleCandidateRecord.digest_rank`
简化理解:
- `ArticleCandidateRecord` 保留证据
- `OpenClawCandidateInput` 保留结论
---
## 8. `DailyDigest` 设计
### 8.1 角色定义
`DailyDigest` 是 OpenClaw 聚合多个 `OpenClawCandidateInput` 后形成的日级主产物。
它不应该再携带单篇全文,也不应该回退到内部调试结构。
### 8.2 建议字段
```json
{
"digest_id": "digest:2026-03-25",
"date": "2026-03-25",
"title": "2026-03-25 阅读日报",
"summary": "今天的输入主要围绕 AI 工具、工程实践和软件产品策略展开。",
"sections": [
{
"section_id": "insights",
"title": "观察与判断",
"summary": "今天更值得关注的是 AI 对软件行业护城河和商业包装的影响。",
"items": [
{
"candidate_id": "cand:sha256:xxx",
"title": "文章标题",
"summary": "单篇摘要压缩版",
"why_it_matters": "为什么今天值得被放进这个栏目",
"action": "值得继续跟进"
}
]
}
],
"top_items": ["cand:sha256:xxx"],
"key_takeaways": [
"摘要层和知识沉淀层应分开。",
"规则证据链应保留在本地,而不是直接下发给聚合器。"
],
"watchlist": [
"继续收敛 paywall 误判。"
],
"candidate_ids": ["cand:sha256:xxx"],
"source_refs": [
{
"candidate_id": "cand:sha256:xxx",
"url": "https://example.com/post/1"
}
],
"editor_notes": "今天的输入以观点和周刊类内容为主。",
"stats": {
"candidate_total": 12,
"kept_total": 4,
"review_total": 6,
"dropped_total": 2
},
"metadata": {
"generated_at": "2026-03-25T21:00:00Z",
"producer": "openclaw",
"pipeline_version": "v2"
}
}
```
### 8.3 `sections.items[]` 子结构建议
```json
{
"candidate_id": "cand:sha256:xxx",
"title": "文章标题",
"summary": "单篇摘要压缩版",
"why_it_matters": "为什么这条内容今天值得看",
"action": "值得试用 / 值得跟进 / 值得收藏 / 待验证"
}
```
这里最关键的不是原始摘要复述,而是 `why_it_matters`。
因为日报的价值不在于再列一遍新闻,而在于表达“今天为什么值得看”。
---
## 9. 为什么这样设计更合理
### 9.1 控制 token 成本
把正文全文挡在 OpenClaw 之前,能显著降低聚合阶段的 token 开销。
### 9.2 保持对象职责单一
- `ArticleCandidateRecord` 负责本地审计
- `OpenClawCandidateInput` 负责下游消费
- `DailyDigest` 负责日级成品
每层只做一件事,后续更容易演进。
### 9.3 降低上下游耦合
OpenClaw 不需要知道本地 `outputs/` 目录结构,也不应该依赖规则引擎的内部细节。
### 9.4 保留调试与重放能力
内部对象依然保留全文、质量标记、完整过滤证据链,因此不会因为“下游精简”而损失工程可维护性。
### 9.5 为后续人审与知识库沉淀留出口
当日报和知识库真正接起来时:
- OpenClaw 基于精简输入做日报聚合
- 人工基于日报成品做最终判断
- 本地记录对象作为审计底稿长期保留
这个边界是清晰且可持续的。
---
## 10. 当前阶段的实现建议
建议按这个顺序推进:
1. 在文档层正式采用这三个对象
2. 将当前代码里的 `article_candidate` 重命名或重新定位为 `ArticleCandidateRecord`
3. 新增 `OpenClawCandidateInput` 模型
4. 增加 `ArticleCandidateRecord -> OpenClawCandidateInput` 的转换逻辑
5. 让 OpenClaw 只消费精简输入对象
6. 后续再补 `DailyDigest` 的真实生成逻辑
---
## 11. 一句话结论
这次改动的本质,不是“删掉几个字段”,而是把“内部候选记录对象”和“发给 OpenClaw 的精简输入对象”彻底分层;只有这样,当前项目才能同时保留审计能力、控制 token 成本,并稳定服务 OpenClaw 的日报聚合。
@@ -0,0 +1,351 @@
# OpenClaw Candidate Input 字段说明
## 1. 文档目的
本文档定义当前项目输出给 OpenClaw 的结构化输入对象:`OpenClawCandidateInput`。
这是一份面向 OpenClaw 消费侧的接口说明文档,不要求了解本项目内部的 `item`、`article`、`filter_result` 等实现细节。
当前定位是:
- 单篇候选内容的精简输入
- 用于 OpenClaw 做日报聚合、排序、栏目分配和后续汇报
- 不承载正文全文、不承载本地文件路径、不承载规则引擎完整证据链
---
## 2. 设计原则
这个 payload 的设计遵循以下原则:
1. 足够轻
- 不发送正文全文,避免浪费 token
2. 足够稳定
- 不暴露本地目录结构和内部中间文件路径
3. 足够可消费
- 字段扁平化,避免 OpenClaw 反复解析嵌套对象
4. 足够有判断信号
- 保留摘要、主题、价值判断、筛选结果、排序信号
5. 足够可去重
- 同时提供原始 `url` 与归一化后的 `canonical_url`
---
## 3. 完整 JSON 示例
```json
{
"candidate_id": "cand:sha256:4139f277b8cb621b02b3398f8a7bd78e3f9eef7bcd320b70b8590e802540c6ca",
"title": "套壳中国大模型撑起500亿美元估值?扒一扒 Cursor 的\"套壳\"疑云",
"url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html?utm_source=rss",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"published_at": "2026-03-21T10:19:11Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": "zh-CN",
"summary": "AI编程工具Cursor推出的Composer 2模型被证实套壳中国Kimi K2.5模型,引发侵权争议。Kimi官方确认Cursor通过Fireworks AI获得授权,不存在侵权。作者分析Cursor隐瞒事实是为了支撑其不断膨胀的估值,将其包装成大模型公司。",
"highlights": [
"Cursor的Composer 2模型被技术手段揭露实际调用的是Kimi K2.5模型。",
"Kimi官方确认Cursor通过Fireworks AI获得授权,因此不构成侵权。",
"Cursor隐瞒使用Kimi模型,被认为是为了支撑其高达500亿美元的估值。"
],
"keywords": ["Cursor", "Composer 2", "Kimi K2.5", "Fireworks AI", "AI编程工具"],
"topics": ["人工智能", "大模型", "商业伦理"],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入剖析了AI行业的热点事件,涉及技术真相、商业动机和行业趋势,具有较高的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": "insights",
"digest_rank": 60
}
```
---
## 4. 字段总览
| 字段名 | 类型 | 必填 | 说明 |
| --- | --- | --- | --- |
| `candidate_id` | `string` | 是 | 单篇候选内容唯一标识 |
| `title` | `string` | 是 | 文章或内容标题 |
| `url` | `string` | 是 | 原始链接 |
| `canonical_url` | `string \| null` | 否 | 归一化链接,用于更稳定的去重 |
| `published_at` | `string \| null` | 否 | 发布时间,ISO 8601 格式 |
| `author` | `string \| null` | 否 | 作者名 |
| `source_name` | `string \| null` | 否 | 来源名称,例如博客名、站点名、Feed 名 |
| `language` | `string \| null` | 否 | 语言标记,例如 `zh-CN`、`en` |
| `summary` | `string` | 是 | 2 到 3 句话的精简摘要 |
| `highlights` | `string[]` | 是 | 3 到 5 条单句要点 |
| `keywords` | `string[]` | 是 | 5 到 8 个关键词 |
| `topics` | `string[]` | 是 | 3 到 5 个高层主题标签 |
| `category` | `string` | 是 | 内容分类 |
| `worth_keeping` | `boolean` | 是 | 摘要层给出的长期保留判断 |
| `worth_reason` | `string` | 是 | 对 `worth_keeping` 的解释 |
| `selection_decision` | `string` | 是 | 规则层压缩后的筛选决策 |
| `selection_reason` | `string \| null` | 否 | 对 `selection_decision` 的简短解释 |
| `digest_section_hint` | `string \| null` | 否 | 建议栏目 |
| `digest_rank` | `integer` | 是 | 建议排序分值,范围 `0-100` |
---
## 5. 字段详细说明
### 5.1 `candidate_id`
含义:
- 单篇候选内容的稳定唯一标识
约束:
- 同一条上游内容在当前系统中应保持稳定
- OpenClaw 可以把它作为去重、回溯、引用的主键
### 5.2 `title`
含义:
- 候选内容标题
来源:
- 优先来自标准化 `item.title`
- 如果上游标题缺失,则退回摘要结果中的 `summary.title`
### 5.3 `url`
含义:
- 原始内容链接
用途:
- OpenClaw 在日报中回链原文
- 后续人工 review 或知识库引用时回溯来源
### 5.4 `canonical_url`
含义:
- 对原始 `url` 做轻量归一化后的链接
当前归一化策略:
- 去掉 fragment
- 去掉常见追踪参数,例如 `utm_*`、`fbclid`、`gclid`、`ref` 等
- 保留其他非追踪 query 参数
用途:
- 让 OpenClaw 在去重时更稳定
- 避免同一篇文章因为带不同追踪参数被当成两篇
说明:
- `url` 保留原始值,`canonical_url` 提供去重辅助
- OpenClaw 建议优先用 `canonical_url` 做去重键,不足时再结合 `candidate_id`
### 5.5 `published_at`
含义:
- 内容发布时间
格式:
- ISO 8601,例如 `2026-03-21T10:19:11Z`
### 5.6 `author`
含义:
- 作者名称
### 5.7 `source_name`
含义:
- 内容来源名称
常见示例:
- `阮一峰的网络日志`
- `FreshRSS`
- 某个 Feed 标题
- 某个站点域名
### 5.8 `language`
含义:
- 语言标记
常见示例:
- `zh`
- `zh-CN`
- `en`
用途:
- OpenClaw 后续处理多语言输入时做风格和分类控制
- 为知识库入库、多语言日报、翻译或过滤策略留出口
说明:
- 如果当前上游无法可靠识别语言,可以为 `null`
### 5.9 `summary`
含义:
- 摘要主文本
约束:
- 当前上游约束是 2 到 3 句话
- 长度不超过 140 个中文字符
### 5.10 `highlights`
含义:
- 关键要点列表
约束:
- 3 到 5 条
- 每条一条独立信息
### 5.11 `keywords`
含义:
- 具体实体、工具名、方法名、关键概念
约束:
- 5 到 8 个
### 5.12 `topics`
含义:
- 高层主题标签
约束:
- 3 到 5 个
- 语义层级高于 `keywords`
### 5.13 `category`
含义:
- 内容分类
当前允许值:
- `资讯`
- `方法论`
- `工具实践`
- `观点评论`
### 5.14 `worth_keeping`
含义:
- 这条内容是否具有持续保留价值
说明:
- 这是摘要层的价值判断,不是最终入库决定
- OpenClaw 可以把它当作优先筛选信号,而不是绝对真值
### 5.15 `worth_reason`
含义:
- 对 `worth_keeping` 的解释
### 5.16 `selection_decision`
含义:
- 规则引擎压缩后的筛选决策
当前允许值:
- `keep`
- `review`
- `drop`
### 5.17 `selection_reason`
含义:
- 对 `selection_decision` 的简短解释
说明:
- 当前一般取规则引擎 reasons 的第一条压缩说明
- 不承诺包含全部规则命中细节
### 5.18 `digest_section_hint`
含义:
- 建议日报栏目
当前允许值:
- `top_news`
- `tools_and_workflows`
- `risk_and_security`
- `open_source`
- `insights`
- `deep_dive`
- `null`
### 5.19 `digest_rank`
含义:
- 建议排序分值
范围:
- `0` 到 `100`
建议解释:
- `80-100`:高优先级,建议优先关注
- `50-79`:中优先级,建议正常进入候选池
- `0-49`:低优先级,建议降权或仅保留参考
---
## 6. OpenClaw 消费建议
推荐 OpenClaw 主要消费这几组信号:
### 6.1 语义聚合信号
- `summary`
- `highlights`
- `keywords`
- `topics`
- `category`
### 6.2 选择与排序信号
- `worth_keeping`
- `worth_reason`
- `selection_decision`
- `selection_reason`
- `digest_rank`
- `digest_section_hint`
### 6.3 来源展示信号
- `title`
- `url`
- `canonical_url`
- `published_at`
- `author`
- `source_name`
- `language`
---
## 7. 当前不会提供的字段
OpenClaw 当前不应期待以下字段:
- 正文全文,例如 `plain_text`
- 本地文件路径,例如 `source_refs`
- 完整规则证据链,例如 `filter_result.matches`
- 内部中间对象,例如完整的 `item`、`article`、`summary`、`filter_result`
- 人工确认状态,例如 `review_status`、`knowledge_decision`
最后一类字段不会放在这个对象中,原因是:
- `OpenClawCandidateInput` 表示的是上游候选事实
- 人工确认和知识沉淀属于下游流程状态
- 两者混在一起会让输入对象逐渐失真、变脏
---
## 8. 兼容性约定
当前版本约定:
- 这是单篇输入对象,不是批量 envelope
- 批量投递由上层 `OpenClawDeliveryPayload` 承载
- 本文档只约束 `candidates[]` 中单条对象的字段
---
## 9. 一句话结论
`OpenClawCandidateInput` 是“给 OpenClaw 聚合日报用的单篇精简对象”:它保留来源信息、摘要语义、价值判断、去重辅助和排序信号,但不会携带正文全文、本地路径、规则证据链或人工确认状态。
@@ -0,0 +1,222 @@
# OpenClaw 日报聚合改造说明
## 1. 为什么要改
当前项目已经跑通了:
`FreshRSS -> item -> extraction -> LLM summary -> validator -> filter -> Markdown sink`
这条链路证明了上游拉取、结构化提取、摘要校验和规则过滤都是可行的。
但如果最终目标是:
- 每日提炼总结进入知识库
- OpenClaw 向用户汇报今天的日报
那么当前“单篇过滤后直接写入本地 Markdown 知识库”的主路径就不够准确了。
原因有四点:
1. 单篇文章更像原材料,不是最终成品
2. 用户要的是“日报级总结 + 知识沉淀”,不是“每篇都直接入库”
3. 参考文章中真正的终态是 `Digest -> Daily Review -> 人工确认 -> Lumina`
4. 当前 `article_candidate` 如果同时承担内部记录和下游投递,会导致 payload 过重、token 过高、边界混乱
所以当前项目要从“单篇直接入库”切换为“单篇候选材料 -> 日报聚合 -> 人工确认 -> 知识沉淀”。
## 2. 参考文章给出的真实结构
参考文章里的关键分层是:
1. `Digest`
- 去重、抓正文、质量检查、生成摘要
- 产出可判断的候选内容
2. `Daily Review`
- 从候选内容中做栏目化精选
- 产出当天的日报
3. `Human in the loop`
- 人工判断哪些内容值得长期保留
4. `Lumina`
- 只承接真正值得长期保留的内容
这意味着:
- 日报不是知识库的替代品
- 知识库也不应该承接所有单篇文章
- 单篇内容更适合作为日报生成前的候选材料
## 3. 当前设计哪里不够
当前的不足主要在下游:
### 3.1 `sink` 语义过重
现在的 `Markdown sink` 更像“最终入库器”。
但在新的目标里,它最多只应扮演:
- debug sink
- fallback sink
- 审计/归档 sink
主路径不应再把它视为最终知识库形态。
### 3.2 缺少“日级对象”
当前项目有:
- `item`
- `article`
- `summary`
- `filter_decision`
但还没有:
- `ArticleCandidateRecord`
- `OpenClawCandidateInput`
- `DailyDigest`
如果没有这三个对象,就无法稳定表达:
- 单篇内容如何作为内部候选材料存在
- 单篇内容如何以低 token 的形式发给 OpenClaw
- 一天的内容如何被聚合为一个正式产物
### 3.3 缺少人工确认层
规则引擎的 `keep` 只能表示“值得进入下一步”,不能直接等价于“正式入知识库”。
如果没有人工确认层,系统就会退化成“规则命中即永久沉淀”,这和参考文章强调的 `Human in the loop` 不一致。
### 3.4 下游输入边界不清楚
如果把正文全文、完整规则证据链、本地文件路径都发给 OpenClaw,会出现三个直接问题:
- token 浪费
- 对象职责混乱
- OpenClaw 输入与本地实现耦合
所以必须把“内部记录对象”和“下游精简输入对象”分开。
## 4. 改造后的主路径
建议主路径调整为:
`FreshRSS/RSS -> extraction -> LLM summary -> validator -> rule engine -> ArticleCandidateRecord -> OpenClawCandidateInput -> OpenClaw -> DailyDigest -> human review -> knowledge base`
这里要注意几件事:
1. 当前项目负责生成高质量候选材料与精简输入
2. OpenClaw 负责按天聚合、生成日报、编排后续动作
3. 知识库只接收日报和人工确认后的长期内容
## 5. 新的对象分层
### 5.1 `ArticleCandidateRecord`
定位:
- 单篇内容的内部候选记录
- 用于留档、追溯、重放、审计
最少应包含:
- `item`
- `article`
- `summary`
- `filter_result`
- `metadata`
- 可选 `source_refs`
- 可选 `rendered_markdown`
### 5.2 `OpenClawCandidateInput`
定位:
- 当前项目发给 OpenClaw 的标准投递对象
- 用于日报聚合与排序
最少应包含:
- `candidate_id`
- `title`
- `url`
- `published_at`
- `author`
- `summary`
- `highlights`
- `topics`
- `category`
- `worth_keeping`
- `selection_decision`
- `selection_reason`
- `digest_section_hint`
- `digest_rank`
它不应包含:
- `article.plain_text`
- `filter_result.matches`
- `source_refs`
### 5.3 `DailyDigest`
定位:
- 一天的主产物
- 同时服务于“知识沉淀”和“日报汇报”
建议至少包含:
- `date`
- `sections`
- `top_items`
- `key_takeaways`
- `watchlist`
- `candidate_ids`
- `source_refs`
- `editor_notes`
## 6. 为什么这样更合理
这样改造有几个直接收益:
1. 知识库不会被大量单篇摘要污染
2. OpenClaw 不需要再次消费全文,token 更可控
3. OpenClaw 的输入边界更清晰,不依赖本地目录结构和规则证据链
4. 当前项目仍然保留完整候选记录,因此误判排查和重放能力不会丢
5. 未来扩展周报、专题文章和反馈回流会更自然
本质上,这是把当前系统从“单篇落库工具”调整为“日报生产链路中的候选记录生产器 + 精简投递器”。
## 7. 对当前实现的影响
不需要推翻已有能力,主要是重新定位:
- `extraction` 保留
- `LLM summary validator` 保留
- `rule engine` 保留
- `FreshRSS integration` 保留
- `Markdown sink` 保留,但降级为调试/回退能力
真正新增的是:
- `ArticleCandidateRecord` schema
- `OpenClawCandidateInput` schema
- `ArticleCandidateRecord -> OpenClawCandidateInput` 映射逻辑
- `DailyDigest` schema
- 人工确认后的状态流转
## 8. 下一步应该做什么
建议按这个顺序推进:
1. 在代码里把当前 `article_candidate` 重新定位为 `ArticleCandidateRecord`
2. 新增 `OpenClawCandidateInput` 模型
3. 增加精简 payload 的本地输出脚本或转换函数
4. 让 OpenClaw 只消费精简输入对象
5. 再设计批量聚合和 `DailyDigest` 生成
## 9. 一句话结论
如果最终目标是“每天有日报汇报,同时把日级提炼沉淀进知识库”,那么当前项目就不该继续围绕“单篇直接入库”演进,而应拆成“内部候选记录对象 + OpenClaw 精简输入对象 + 日级成品对象”三层结构。
@@ -0,0 +1,195 @@
# OpenClaw Delivery Payload 字段说明
## 1. 文档目的
本文档定义当前项目批量投递给 OpenClaw 的外层 envelope:`OpenClawDeliveryPayload`。
它不是单篇 candidate 对象,而是承载一批 `OpenClawCandidateInput` 的批次对象。
---
## 2. 完整 JSON 示例
```json
{
"schema_version": "v1",
"generated_at": "2026-03-26T10:15:30Z",
"run_id": "openclaw-delivery-20260325-101530",
"date": "2026-03-25",
"candidates": [
{
"candidate_id": "cand:sha256:xxx",
"title": "文章标题",
"url": "https://example.com/post",
"canonical_url": "https://example.com/post",
"published_at": "2026-03-25T09:30:00Z",
"author": "作者",
"source_name": "来源",
"language": "zh-CN",
"summary": "2 到 3 句话摘要",
"highlights": ["要点1", "要点2", "要点3"],
"keywords": ["关键词1", "关键词2", "关键词3", "关键词4", "关键词5"],
"topics": ["主题1", "主题2", "主题3"],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "有长期参考价值",
"selection_decision": "review",
"selection_reason": "worth_keeping=true but no stronger keep rule matched",
"digest_section_hint": "insights",
"digest_rank": 60
}
],
"stats": {
"total": 1,
"keep_total": 0,
"review_total": 1,
"drop_total": 0
}
}
```
---
## 3. 字段总览
| 字段名 | 类型 | 必填 | 说明 |
| --- | --- | --- | --- |
| `schema_version` | `string` | 是 | 当前 envelope 的 schema 版本 |
| `generated_at` | `string` | 是 | 本批数据的生成时间,ISO 8601 格式 |
| `run_id` | `string` | 是 | 本次批量投递的唯一运行标识 |
| `date` | `string` | 是 | 本批次所属日期,格式 `YYYY-MM-DD` |
| `candidates` | `OpenClawCandidateInput[]` | 是 | 单篇候选内容列表 |
| `stats` | `object` | 是 | 批次级统计信息 |
---
## 4. 字段详细说明
### 4.1 `schema_version`
含义:
- 当前批量 envelope 的结构版本
用途:
- 未来字段调整时做兼容处理
- 让 OpenClaw 能按版本选择不同解析逻辑
当前值:
- `v1`
### 4.2 `generated_at`
含义:
- 本批数据的实际生成时间
格式:
- ISO 8601,例如 `2026-03-26T10:15:30Z`
用途:
- 排查数据新旧
- 增量处理
- 失败重跑和批次比对
### 4.3 `run_id`
含义:
- 本次投递任务的唯一标识
用途:
- 失败重跑追踪
- 批次去重
- 运行日志关联
建议:
- 由上游在每次批量生成时唯一产生
- 例如:`openclaw-delivery-20260325-101530`
### 4.4 `date`
含义:
- 本批次所属日期
格式:
- `YYYY-MM-DD`
用途:
- OpenClaw 进行日报归档
- 将多次投递映射到同一天的 digest 流程
### 4.5 `candidates`
含义:
- 单篇候选输入对象列表
说明:
- 数组内每个元素都应满足 `OpenClawCandidateInput` 定义
- 单篇字段说明请参考:
- `docs/openclaw/openclaw-candidate-input-field-spec.md`
### 4.6 `stats`
含义:
- 本批次的统计信息
当前字段包括:
- `total`
- `keep_total`
- `review_total`
- `drop_total`
用途:
- OpenClaw 在接收后快速感知这批输入的规模和分布
- 便于记录运行状态和对账
---
## 5. `stats` 子结构说明
| 字段名 | 类型 | 必填 | 说明 |
| --- | --- | --- | --- |
| `total` | `integer` | 是 | candidate 总数 |
| `keep_total` | `integer` | 是 | `selection_decision=keep` 的数量 |
| `review_total` | `integer` | 是 | `selection_decision=review` 的数量 |
| `drop_total` | `integer` | 是 | `selection_decision=drop` 的数量 |
说明:
- 这些统计值由上游根据 `candidates[]` 自动汇总
- OpenClaw 可以直接信任,也可以再次校验
---
## 6. 推荐消费方式
建议 OpenClaw 的批处理逻辑按以下顺序进行:
1. 先读取 `schema_version`
- 选择对应版本的解析逻辑
2. 再读取 `generated_at`、`run_id` 和 `date`
- 建立本次批处理上下文
3. 再读取 `stats`
- 快速判断这批输入规模与分布
4. 最后逐条消费 `candidates[]`
- 去重
- 聚类
- 分栏目
- 排序
- 产生日报和 review 清单
---
## 7. 当前不会放入 envelope 的字段
当前 envelope 不会额外放入:
- 完整内部候选记录列表
- 人工确认状态列表
- 知识库入库状态列表
- 执行日志文本
这些都属于其他层的对象,不应混进上游投递协议。
---
## 8. 一句话结论
`OpenClawDeliveryPayload` 是“给 OpenClaw 的批量投递对象”:它用 `schema_version`、`generated_at`、`run_id`、`date`、`stats` 管理批次上下文,用 `candidates[]` 承载真正的单篇候选输入。
+129
View File
@@ -0,0 +1,129 @@
我看了,这版 可以,方向是对的。
如果这是“上游项目 → OpenClaw”的输入格式,我觉得已经 基本能直接用了。
我的判断:
这版为什么合适
它正好满足我最需要的几类信息:
来源信息:title / url / published_at / author / source_name
语义理解:summary / highlights / keywords / topics / category
筛选排序信号:worth_keeping / worth_reason / selection_decision / selection_reason / digest_rank / digest_section_hint
用这批字段,我已经可以做:
日报聚合
去重
分栏目
排序
生成你的 review 清单
供你确认后再沉淀到知识库
所以单从“我好不好解析、能不能稳定消费”来说,
这版 JSON 明显比 md 更适合当上游输入。
我建议你保留的设计
这几个点我觉得是对的,不要轻易改掉:
单篇 candidate 扁平对象
非常适合我消费
不用反复钻嵌套
不带全文
对,别把正文全文塞进来
token 开销会爆,而且日报阶段根本不需要
同时保留语义字段 + 筛选字段
summary/highlights/topics 让我理解内容
selection_decision/digest_rank 让我快速决定怎么排
candidate_id 作为稳定主键
这个非常重要
后续你让我“保留第几条”“这条上次见过没”“已入库没”都靠它
我建议你再补 4 个点
这版已经能用,但如果你要长期跑,我建议再补几个小点。
1)加一个批量 envelope
你文档里其实已经提到了,我建议尽快定下来。
比如:
{
"run_id": "daily-2026-03-25-001",
"date": "2026-03-25",
"candidates": [ ... ],
"stats": {
"total": 42
}
}
原因:
我实际处理日报,不会只收一条
批次级信息对去重、追踪、失败重跑很重要
2)加一个 canonical_url 或 url_normalized
现在只有 url,但很多站点会有追踪参数。
建议补一个:
canonical_url或
url_normalized
原因:
去重更稳
同一篇文章不同 query 参数不会被当两篇
3)加一个 language
比如:
"language": "zh-CN"
原因:
以后你来源不一定全是中文
我做日报、摘要风格、后续入知识库时会更稳
4)“用户确认结果”不要塞回这个输入对象里
这个很关键。
你这个 OpenClawCandidateInput 很适合做 上游候选输入,
但“你后来确认它有价值”这件事,我建议 不要回写进这个对象定义里。
更好的做法是单独维护 downstream 状态,比如:
{
"candidate_id": "...",
"review_status": "confirmed",
"reviewed_at": "...",
"review_note": "保留,适合入知识库"
}
原因:
上游输入是“候选事实”
你的确认是“流程状态”
这两个层次最好分开,不然对象会慢慢变脏
有一个字段关系,我建议你保留现状
就是:
worth_keeping
selection_decision
这两个不要合并。
因为它们语义不一样:
worth_keeping:更像摘要层/语义层判断
selection_decision:更像规则层/流程层判断
我消费的时候,两者同时有用。
如果按你的目标流程,我建议最终这么分层
上游输入
用你现在这版 JSON candidate
OpenClaw 中间处理
我生成:
日报 markdown
待你确认的候选列表
人工确认后
再生成:
知识卡片对象
或笔记对象
再入知识库
也就是说:
候选输入 JSON ≠ 最终知识库格式
别把“日报候选格式”和“知识沉淀格式”硬合成一个。
一句话结论
这版 JSON 作为上游输入,已经比 md 合适很多,而且基本可落地。
如果再补上:
批量 envelope
canonical_url
language
下游确认状态单独建模
那这套就很稳了。
+38
View File
@@ -0,0 +1,38 @@
# Outputs Layout
`outputs/` 按“来源 + 阶段”分层,避免所有中间产物堆在根目录。
## 目录约定
- `outputs/prompts/`
- prompt 模板与调试输入
- `outputs/reference/`
- 手工样例、固定参考输入、通用演示产物
- `outputs/reference/extracted/`
- 参考提取结果
- `outputs/reference/summary/`
- 通用摘要结果与 loop 调试产物
- `outputs/reference/filter/`
- 通用过滤结果与上下文样例
- `outputs/reference/candidates/`
- 通用 `article_candidate` 样例
- `outputs/freshrss/`
- FreshRSS 实跑产物
- `outputs/freshrss/raw/`
- greader 原始响应
- `outputs/freshrss/items/`
- entry -> `item` 映射结果
- `outputs/freshrss/extracted/`
- FreshRSS 文章提取结果
- `outputs/freshrss/summary/`
- FreshRSS 摘要 loop 结果与调试文件
- `outputs/freshrss/filter/`
- FreshRSS 过滤结果
- `outputs/freshrss/candidates/`
- FreshRSS `article_candidate` 结果
## 命名原则
- 默认脚本输出应优先写入对应子目录,不再直接写 `outputs/` 根目录。
- 同一条链路的调试文件放在同一阶段目录里,例如 `result.loop.json` 与 `result.loop.attempt-*.json`。
- `reference/` 只放可复用的稳定样例,真实运行数据优先放 `freshrss/`。
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,42 @@
{
"candidate_id": "cand:sha256:4139f277b8cb621b02b3398f8a7bd78e3f9eef7bcd320b70b8590e802540c6ca",
"title": "套壳中国大模型撑起500亿美元估值?扒一扒 Cursor 的\"套壳\"疑云",
"url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"published_at": "2026-03-21T10:19:11Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "AI编程工具Cursor推出的Composer 2模型被证实套壳中国Kimi K2.5模型,引发侵权争议。Kimi官方确认Cursor通过Fireworks AI获得授权,不存在侵权。作者分析Cursor隐瞒事实是为了支撑其不断膨胀的估值,将其包装成大模型公司。",
"highlights": [
"Cursor的Composer 2模型被技术手段揭露实际调用的是Kimi K2.5模型。",
"Kimi官方确认Cursor通过Fireworks AI获得授权,因此不构成侵权。",
"Cursor隐瞒使用Kimi模型,被认为是为了支撑其高达500亿美元的估值。",
"事件显示中国大模型技术已具备输出能力,国产模型与国外旗舰差距缩小。",
"Composer 2性能低于GPT-5.4但成本最低,生成速度较快。"
],
"keywords": [
"Cursor",
"Composer 2",
"Kimi K2.5",
"Fireworks AI",
"套壳模型",
"模型授权",
"估值泡沫",
"AI编程工具"
],
"topics": [
"人工智能",
"大模型",
"商业伦理",
"技术争议",
"创业融资"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入剖析了AI行业的热点事件,涉及技术真相、商业动机和行业趋势,具有较高的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,42 @@
{
"candidate_id": "cand:sha256:a16942c9699333155498d2bc59c530358bd6d81d9afe01e2b96e0e862edfc6a6",
"title": "科技爱好者周刊(第 389 期):未来如何招聘程序员",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"published_at": "2026-03-19T23:59:16Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "本文探讨了在AI编程普及的未来,如何招聘和面试程序员。作者认为考察重点应从代码能力转向AI使用、架构理解和需求转化能力。文章指出传统面试方法面临挑战,并引发了对未来程序员核心技能的思考。",
"highlights": [
"未来程序员招聘的重点可能从代码能力转向AI工具的使用熟练度。",
"面试问题需要考察将复杂需求转化为清晰提示词的能力。",
"AI编程时代,对系统架构知识和项目分解能力的要求依然重要。",
"传统的编程语法细节考察在AI辅助下意义可能减弱。",
"文章引发了关于AI如何颠覆软件开发及人才评估标准的讨论。"
],
"keywords": [
"AI编程",
"程序员招聘",
"面试问题",
"提示词工程",
"Skill",
"MCP",
"多Agent协同",
"系统架构"
],
"topics": [
"人工智能",
"软件开发",
"职业发展",
"技术趋势",
"人才评估"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入探讨了AI时代程序员招聘的前瞻性问题,具有启发性和讨论价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,42 @@
{
"candidate_id": "cand:sha256:0d315d9489010cfd470a8d479e4e4443722fffdc34ecc1245c1b92458ace5093",
"title": "科技爱好者周刊(第 388 期):测试是新的护城河",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"published_at": "2026-03-12T23:59:16Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "本文以 Cloudflare 工程师用 AI 在一周内复刻 Next.js 框架为例,指出 AI 使得代码的护城河不复存在。作者认为,软件公司未来将依赖保密的测试用例来防止 AI 复刻,测试成为新的竞争壁垒。",
"highlights": [
"Cloudflare 工程师仅用一周时间和 1100 美元 Token 费用,通过 AI 成功复刻了 Next.js 框架,性能优于原版。",
"AI 能够复刻软件的关键在于开源项目提供了完备的文档、社区文章和测试用例,使得 API 兼容性得以验证。",
"为防止 AI 复刻,大型软件项目可能选择将核心测试用例闭源,如 SQLite 的 TH3 测试套件和 tldraw 的计划。",
"AI 复刻软件引发了版权争议,例如 chardet 项目的许可证更改,且美国法律认定 AI 生成物无版权,冲击现有许可证体系。",
"文章还讨论了 AI 对软件行业的多方面影响,包括提高效率、替代岗位以及可能引发的社会复杂性崩溃问题。"
],
"keywords": [
"Next.js",
"AI 复刻",
"测试用例",
"SQLite",
"MIT 许可证",
"Cloudflare",
"vinext",
"护城河"
],
"topics": [
"人工智能",
"软件开发",
"开源协议",
"技术趋势",
"行业影响"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入探讨了 AI 对软件行业护城河的颠覆性影响,并提出了测试用例作为新壁垒的见解,具有前瞻性和讨论价值。",
"selection_decision": "review",
"selection_reason": "Article may be behind a paywall.",
"digest_section_hint": null,
"digest_rank": 95
}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,42 @@
{
"candidate_id": "cand:sha256:419828361de854cd29dbcd3e8205d3da50ff955ac9c85861d2e195bc888b2103",
"title": "FreshRSS 1.28.1",
"url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.1",
"canonical_url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.1",
"published_at": "2026-01-25T18:20:16Z",
"author": "Alkarex",
"source_name": "FreshRSS releases",
"language": null,
"summary": "FreshRSS 1.28.1 是一个专注于修复错误的版本,主要解决了 1.28.0 版本引入的回归问题。该版本包含少量新功能、性能改进和多项错误修复。",
"highlights": [
"此版本主要修复了 1.28.0 版本引入的回归问题。",
"新增了注册关闭时的可自定义消息功能。",
"在 Apache 访问日志和 Docker 日志中添加了用户名记录。",
"通过禁用 Ajax 请求中用户标签的文章计数来提升性能。",
"修复了包括用户查询扩展、标签搜索、令牌访问在内的多项错误。"
],
"keywords": [
"FreshRSS",
"bug fixing",
"regression",
"Apache logs",
"GReader API",
"Ajax",
"MySQL",
"MariaDB"
],
"topics": [
"开源软件",
"版本更新",
"RSS 阅读器",
"软件开发",
"性能优化"
],
"category": "资讯",
"worth_keeping": true,
"worth_reason": "提供了 FreshRSS 特定版本更新的详细变更信息,对用户和开发者有明确的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,42 @@
{
"candidate_id": "cand:sha256:6b36071bbd22c58692c039e172669ae28ac1ec8a6a6bce150c22d80af29761fc",
"title": "FreshRSS 1.28.0",
"url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.0",
"canonical_url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.0",
"published_at": "2025-12-24T19:27:23Z",
"author": "Alkarex",
"source_name": "FreshRSS releases",
"language": null,
"summary": "FreshRSS 1.28.0 是一个主要版本更新,引入了按用户修改日期排序、高级搜索表单等新功能,并改进了性能和安全性。此版本还包含多项错误修复,并更新了Docker默认镜像。",
"highlights": [
"新增按用户修改日期排序和过滤功能,并支持对应的搜索操作符。",
"引入了新的高级搜索表单和文章长度排序选项。",
"改进了用户统计的扩展性,以支持拥有1000名以上用户的实例。",
"修复了OpenID Connect在Debian 13上的兼容性问题。",
"Docker默认镜像已更新至Debian 13 Trixie和PHP 8.4.11。"
],
"keywords": [
"FreshRSS",
"用户修改日期排序",
"高级搜索表单",
"Docker",
"Debian 13",
"PHP 8.4",
"OpenID Connect",
"性能优化"
],
"topics": [
"开源软件",
"RSS阅读器",
"版本发布",
"软件开发",
"系统部署"
],
"category": "资讯",
"worth_keeping": true,
"worth_reason": "该文章详细记录了FreshRSS一个重要版本的功能更新、性能改进和错误修复,对用户和开发者具有明确的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
}
@@ -0,0 +1,222 @@
{
"run_id": "openclaw-delivery-20260325-102553",
"date": "2026-03-25",
"candidates": [
{
"candidate_id": "cand:sha256:0d315d9489010cfd470a8d479e4e4443722fffdc34ecc1245c1b92458ace5093",
"title": "科技爱好者周刊(第 388 期):测试是新的护城河",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"published_at": "2026-03-12T23:59:16Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "本文以 Cloudflare 工程师用 AI 在一周内复刻 Next.js 框架为例,指出 AI 使得代码的护城河不复存在。作者认为,软件公司未来将依赖保密的测试用例来防止 AI 复刻,测试成为新的竞争壁垒。",
"highlights": [
"Cloudflare 工程师仅用一周时间和 1100 美元 Token 费用,通过 AI 成功复刻了 Next.js 框架,性能优于原版。",
"AI 能够复刻软件的关键在于开源项目提供了完备的文档、社区文章和测试用例,使得 API 兼容性得以验证。",
"为防止 AI 复刻,大型软件项目可能选择将核心测试用例闭源,如 SQLite 的 TH3 测试套件和 tldraw 的计划。",
"AI 复刻软件引发了版权争议,例如 chardet 项目的许可证更改,且美国法律认定 AI 生成物无版权,冲击现有许可证体系。",
"文章还讨论了 AI 对软件行业的多方面影响,包括提高效率、替代岗位以及可能引发的社会复杂性崩溃问题。"
],
"keywords": [
"Next.js",
"AI 复刻",
"测试用例",
"SQLite",
"MIT 许可证",
"Cloudflare",
"vinext",
"护城河"
],
"topics": [
"人工智能",
"软件开发",
"开源协议",
"技术趋势",
"行业影响"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入探讨了 AI 对软件行业护城河的颠覆性影响,并提出了测试用例作为新壁垒的见解,具有前瞻性和讨论价值。",
"selection_decision": "review",
"selection_reason": "Article may be behind a paywall.",
"digest_section_hint": null,
"digest_rank": 95
},
{
"candidate_id": "cand:sha256:4139f277b8cb621b02b3398f8a7bd78e3f9eef7bcd320b70b8590e802540c6ca",
"title": "套壳中国大模型撑起500亿美元估值?扒一扒 Cursor 的\"套壳\"疑云",
"url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"published_at": "2026-03-21T10:19:11Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "AI编程工具Cursor推出的Composer 2模型被证实套壳中国Kimi K2.5模型,引发侵权争议。Kimi官方确认Cursor通过Fireworks AI获得授权,不存在侵权。作者分析Cursor隐瞒事实是为了支撑其不断膨胀的估值,将其包装成大模型公司。",
"highlights": [
"Cursor的Composer 2模型被技术手段揭露实际调用的是Kimi K2.5模型。",
"Kimi官方确认Cursor通过Fireworks AI获得授权,因此不构成侵权。",
"Cursor隐瞒使用Kimi模型,被认为是为了支撑其高达500亿美元的估值。",
"事件显示中国大模型技术已具备输出能力,国产模型与国外旗舰差距缩小。",
"Composer 2性能低于GPT-5.4但成本最低,生成速度较快。"
],
"keywords": [
"Cursor",
"Composer 2",
"Kimi K2.5",
"Fireworks AI",
"套壳模型",
"模型授权",
"估值泡沫",
"AI编程工具"
],
"topics": [
"人工智能",
"大模型",
"商业伦理",
"技术争议",
"创业融资"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入剖析了AI行业的热点事件,涉及技术真相、商业动机和行业趋势,具有较高的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
},
{
"candidate_id": "cand:sha256:a16942c9699333155498d2bc59c530358bd6d81d9afe01e2b96e0e862edfc6a6",
"title": "科技爱好者周刊(第 389 期):未来如何招聘程序员",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"published_at": "2026-03-19T23:59:16Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "本文探讨了在AI编程普及的未来,如何招聘和面试程序员。作者认为考察重点应从代码能力转向AI使用、架构理解和需求转化能力。文章指出传统面试方法面临挑战,并引发了对未来程序员核心技能的思考。",
"highlights": [
"未来程序员招聘的重点可能从代码能力转向AI工具的使用熟练度。",
"面试问题需要考察将复杂需求转化为清晰提示词的能力。",
"AI编程时代,对系统架构知识和项目分解能力的要求依然重要。",
"传统的编程语法细节考察在AI辅助下意义可能减弱。",
"文章引发了关于AI如何颠覆软件开发及人才评估标准的讨论。"
],
"keywords": [
"AI编程",
"程序员招聘",
"面试问题",
"提示词工程",
"Skill",
"MCP",
"多Agent协同",
"系统架构"
],
"topics": [
"人工智能",
"软件开发",
"职业发展",
"技术趋势",
"人才评估"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入探讨了AI时代程序员招聘的前瞻性问题,具有启发性和讨论价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
},
{
"candidate_id": "cand:sha256:419828361de854cd29dbcd3e8205d3da50ff955ac9c85861d2e195bc888b2103",
"title": "FreshRSS 1.28.1",
"url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.1",
"canonical_url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.1",
"published_at": "2026-01-25T18:20:16Z",
"author": "Alkarex",
"source_name": "FreshRSS releases",
"language": null,
"summary": "FreshRSS 1.28.1 是一个专注于修复错误的版本,主要解决了 1.28.0 版本引入的回归问题。该版本包含少量新功能、性能改进和多项错误修复。",
"highlights": [
"此版本主要修复了 1.28.0 版本引入的回归问题。",
"新增了注册关闭时的可自定义消息功能。",
"在 Apache 访问日志和 Docker 日志中添加了用户名记录。",
"通过禁用 Ajax 请求中用户标签的文章计数来提升性能。",
"修复了包括用户查询扩展、标签搜索、令牌访问在内的多项错误。"
],
"keywords": [
"FreshRSS",
"bug fixing",
"regression",
"Apache logs",
"GReader API",
"Ajax",
"MySQL",
"MariaDB"
],
"topics": [
"开源软件",
"版本更新",
"RSS 阅读器",
"软件开发",
"性能优化"
],
"category": "资讯",
"worth_keeping": true,
"worth_reason": "提供了 FreshRSS 特定版本更新的详细变更信息,对用户和开发者有明确的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
},
{
"candidate_id": "cand:sha256:6b36071bbd22c58692c039e172669ae28ac1ec8a6a6bce150c22d80af29761fc",
"title": "FreshRSS 1.28.0",
"url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.0",
"canonical_url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.0",
"published_at": "2025-12-24T19:27:23Z",
"author": "Alkarex",
"source_name": "FreshRSS releases",
"language": null,
"summary": "FreshRSS 1.28.0 是一个主要版本更新,引入了按用户修改日期排序、高级搜索表单等新功能,并改进了性能和安全性。此版本还包含多项错误修复,并更新了Docker默认镜像。",
"highlights": [
"新增按用户修改日期排序和过滤功能,并支持对应的搜索操作符。",
"引入了新的高级搜索表单和文章长度排序选项。",
"改进了用户统计的扩展性,以支持拥有1000名以上用户的实例。",
"修复了OpenID Connect在Debian 13上的兼容性问题。",
"Docker默认镜像已更新至Debian 13 Trixie和PHP 8.4.11。"
],
"keywords": [
"FreshRSS",
"用户修改日期排序",
"高级搜索表单",
"Docker",
"Debian 13",
"PHP 8.4",
"OpenID Connect",
"性能优化"
],
"topics": [
"开源软件",
"RSS阅读器",
"版本发布",
"软件开发",
"系统部署"
],
"category": "资讯",
"worth_keeping": true,
"worth_reason": "该文章详细记录了FreshRSS一个重要版本的功能更新、性能改进和错误修复,对用户和开发者具有明确的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
}
],
"stats": {
"total": 5,
"keep_total": 0,
"review_total": 5,
"drop_total": 0
}
}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,32 @@
{
"success": true,
"article": {
"extract_id": "sha256:169f2b50eec3d198df126a8daedb95c48cff252ead9d4d2598a449e128cae2b8",
"item_id": "sha256:419828361de854cd29dbcd3e8205d3da50ff955ac9c85861d2e195bc888b2103",
"source_id": "freshrss:2987af960359c5c0",
"url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.1",
"title": "FreshRSS 1.28.1",
"author": "Alkarex",
"published_at": "2026-01-25T18:20:16Z",
"language": null,
"content_kind": "article",
"plain_text": "Alkarex\nreleased this\n25 Jan 18:20\n·\n78 commits\nto edge\nsince this release\nImmutable\nrelease. Only release title and notes can be modified.\nThis is a release focussing on bug fixing, in particular regressions from the release 1.28.0.\nSelected new features ✨:\n- New customisable message for closed registrations\n- Add username in Apache access logs (also in Docker logs): for GReader API, and for HTTP Basic Auth from reverse proxy\nImproved performance 🏎️:\n- Disable counting articles in user labels for Ajax requests (unused)\nMany bug fixes 🐛\nThis release has been made by @Alkarex, @Frenzie, @Inverle and newcomers @ciro-mota, @eveiscoull, @hackerman70000, @Hufschmidt, @johan456789, @martgnz, @mmeier86, @netsho, @neuhaus, @RobLoach, @rupakbajgain.\nFull changelog:\n- Features\n- Bug fixing\n- Fix unwanted expansion of user queries (saved searches) applied to filters #8395\n- Fix encoding of filter actions for labels #8368\n- Fix searching of tags #8425\n- Fix refreshing feeds with token while anonymous refresh is disabled #8371\n- Fix RSS and OPML access by token #8434\n- Fix MySQL/MariaDB\ntransliterator_transliterate\nfallback (when thephp-intl\nextension is unavailable) #8427 - Fix regression with MySQL/MariaDB index hint #8460\n- Auto-add\nlastUserModified\ndatabase column also during mark-as-read action #8346 - Do not include hidden feeds when counting unread articles in categories #8357\n- Remove wrong PHP deprecation of OPML export action #8399\n- Fix shortcut for next unread article #8466\n- Fix custom\nsession.cookie-lifetime\n#8446 - Fix feed validator button when changing the feed URL #8436\n- Performance\n- Disable counting articles in user labels for Ajax requests (unused) #8352\n- Security\n- Deployment\n- Add username in Apache access logs (also in Docker logs): for GReader API, and for HTTP Basic Auth from reverse proxy #8392\n- SimplePie\n- Update of\nCURLOPT_ACCEPT_ENCODING\n#8376, simplepie#960, simplepie#962 - Fix don’t preserve children inside disallowed\n<template>\nelement #8443 - Fixes before PHPStan 2 #8445, simplepie#957\n- Update of\n- Extensions\n- Update\n.gitignore\nto ignore installed extensions #8372\n- Update\n- UI\n- I18n\n- Misc.",
"quality_flags": {
"is_paywalled": false,
"is_truncated": false,
"is_low_content": false
},
"metadata": {
"content_source": "fetched_html",
"extractor": "trafilatura",
"char_count": 2155
},
"pipeline_state": "extracted"
},
"error": null,
"debug": {
"content_source": "fetched_html",
"extractor": "trafilatura"
},
"warnings": []
}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,26 @@
{
"decision": "review",
"matched_rules": [
"review-worth-keeping-other"
],
"reasons": [
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"summary"
],
"priority": 60,
"matches": [
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
@@ -0,0 +1,26 @@
{
"decision": "review",
"matched_rules": [
"review-worth-keeping-other"
],
"reasons": [
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"summary"
],
"priority": 60,
"matches": [
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
@@ -0,0 +1,40 @@
{
"decision": "review",
"matched_rules": [
"review-paywalled-content",
"review-worth-keeping-other"
],
"reasons": [
"Article may be behind a paywall.",
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"paywall",
"quality",
"summary"
],
"priority": 95,
"matches": [
{
"rule_id": "review-paywalled-content",
"decision": "review",
"reason": "Article may be behind a paywall.",
"labels": [
"quality",
"paywall"
],
"priority": 95
},
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
@@ -0,0 +1,26 @@
{
"decision": "review",
"matched_rules": [
"review-worth-keeping-other"
],
"reasons": [
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"summary"
],
"priority": 60,
"matches": [
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
@@ -0,0 +1,26 @@
{
"decision": "review",
"matched_rules": [
"review-worth-keeping-other"
],
"reasons": [
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"summary"
],
"priority": 60,
"matches": [
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
@@ -0,0 +1,26 @@
{
"decision": "review",
"matched_rules": [
"review-worth-keeping-other"
],
"reasons": [
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"summary"
],
"priority": 60,
"matches": [
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -1,6 +1,6 @@
{
"id": "user/-/state/com.google/reading-list",
"updated": 1774346070,
"updated": 1774424530,
"items": [
{
"id": "tag:google.com,2005:reader/item/00064dc1a1f5c0dd",
File diff suppressed because one or more lines are too long
@@ -0,0 +1,42 @@
{
"candidate_id": "cand:sha256:4139f277b8cb621b02b3398f8a7bd78e3f9eef7bcd320b70b8590e802540c6ca",
"title": "套壳中国大模型撑起500亿美元估值?扒一扒 Cursor 的\"套壳\"疑云",
"url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"published_at": "2026-03-21T10:19:11Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "AI编程工具Cursor推出的Composer 2模型被揭露实为套壳中国模型Kimi K2.5。尽管Cursor通过合作伙伴获得授权未侵权,但其隐瞒行为被认为是为支撑高估值而包装成自研模型公司。事件引发对国产大模型技术输出和信心的讨论。",
"highlights": [
"Cursor的Composer 2模型被技术手段揭露实际请求的模型ID为Kimi K2.5。",
"Cursor通过Fireworks AI获得Kimi授权,未违反许可条款,但刻意隐瞒使用事实。",
"Cursor估值在短期内从数千万美元飙升至数百亿美元,有动机包装自研能力以支撑估值。",
"事件显示中国大模型技术已能对外输出,国产模型与国外旗舰差距正在缩小。",
"Kimi在此事件中获得大量曝光,其下一代K3模型被期待有显著性能提升。"
],
"keywords": [
"Cursor",
"Composer 2",
"Kimi K2.5",
"Fireworks AI",
"模型套壳",
"MIT许可证",
"估值泡沫",
"AI编程工具"
],
"topics": [
"人工智能",
"大模型",
"商业伦理",
"技术授权",
"创业融资"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入剖析了AI行业热点事件,涉及技术真相、商业动机和产业趋势,具有较高的讨论和参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
}
File diff suppressed because one or more lines are too long
@@ -0,0 +1,42 @@
{
"candidate_id": "cand:sha256:a16942c9699333155498d2bc59c530358bd6d81d9afe01e2b96e0e862edfc6a6",
"title": "科技爱好者周刊(第 389 期):未来如何招聘程序员",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"published_at": "2026-03-19T23:59:16Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "本文探讨了在AI编程普及的未来,如何有效招聘程序员。作者认为传统的代码能力考察将不再重要,面试重点应转向考察应聘者使用AI工具、分解项目需求以及系统架构的能力。文章也指出,目前尚难确定一套能可靠筛选合格AI编程人才的面试问题。",
"highlights": [
"未来程序员招聘的核心考察点将从手写代码能力转向熟练运用AI工具的能力。",
"面试问题可能包括如何将复杂需求转化为清晰的提示词,以及设计多Agent协同工作机制。",
"传统的编程语法细节考察意义下降,系统架构知识和项目经验可能仍是重要参考。",
"AI的快速发展使得软件开发流程和人才评估标准面临颠覆性变化。",
"文章还包含科技动态、工具推荐、资源分享等周刊常规栏目内容。"
],
"keywords": [
"AI编程",
"程序员招聘",
"面试问题",
"提示词工程",
"多Agent协同",
"系统架构",
"科技动态",
"工具推荐"
],
"topics": [
"人工智能",
"软件开发",
"职业发展",
"科技资讯",
"效率工具"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入探讨了AI时代对程序员职业及招聘流程的潜在影响,具有前瞻性和讨论价值,且内容结构完整、信息量丰富。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
}
File diff suppressed because one or more lines are too long
@@ -0,0 +1,42 @@
{
"candidate_id": "cand:sha256:0d315d9489010cfd470a8d479e4e4443722fffdc34ecc1245c1b92458ace5093",
"title": "科技爱好者周刊(第 388 期):测试是新的护城河",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"published_at": "2026-03-12T23:59:16Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "本期讨论了AI快速复刻大型软件的现象,以Cloudflare工程师一周内用AI重写Next.js为例。文章指出,完备的测试用例成为软件公司防止AI复刻的新护城河,并探讨了AI复刻带来的版权问题。",
"highlights": [
"Cloudflare工程师仅用一周和1100美元Token费用,通过AI复刻了Next.js,性能优于原版。",
"软件护城河从代码转向测试用例,例如SQLite的闭源测试套件TH3是其难以复刻的核心。",
"AI复刻软件引发版权争议,如chardet项目因许可证更改产生纠纷,且AI生成物可能无版权。",
"文章列举了多个科技动态,包括AI改写脏话、激光飞机上网、数字分身争议等。",
"周刊还包含工具推荐、资源分享及读者评论,探讨了AI对程序员行业的影响。"
],
"keywords": [
"Next.js",
"AI复刻",
"测试用例",
"SQLite",
"MIT许可证",
"Cloudflare",
"vinext",
"护城河"
],
"topics": [
"人工智能",
"软件开发",
"开源技术",
"科技趋势",
"版权法律"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入分析了AI对软件行业的冲击,提出了测试作为新护城河的见解,具有前瞻性和讨论价值。",
"selection_decision": "review",
"selection_reason": "Article may be behind a paywall.",
"digest_section_hint": null,
"digest_rank": 95
}
File diff suppressed because one or more lines are too long
@@ -0,0 +1,42 @@
{
"candidate_id": "cand:sha256:419828361de854cd29dbcd3e8205d3da50ff955ac9c85861d2e195bc888b2103",
"title": "FreshRSS 1.28.1",
"url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.1",
"canonical_url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.1",
"published_at": "2026-01-25T18:20:16Z",
"author": "Alkarex",
"source_name": "FreshRSS releases",
"language": null,
"summary": "FreshRSS 1.28.1 是一个专注于修复错误的版本,主要解决了 1.28.0 版本引入的回归问题。该版本包含少量新功能,如可自定义的注册关闭消息,并进行了性能优化。",
"highlights": [
"此版本主要修复了 1.28.0 版本引入的多个回归错误。",
"新增了可自定义的注册关闭消息和 Apache 访问日志中的用户名记录功能。",
"通过禁用 Ajax 请求中用户标签的文章计数来提升性能。",
"修复了涉及过滤器、标签搜索、RSS/OPML 访问和数据库等多个具体问题。",
"该版本由多位贡献者共同完成,包括新加入的开发者。"
],
"keywords": [
"FreshRSS",
"bug 修复",
"回归问题",
"GReader API",
"HTTP Basic Auth",
"Ajax 请求",
"MySQL",
"MariaDB"
],
"topics": [
"开源软件",
"版本更新",
"RSS 阅读器",
"软件开发",
"性能优化"
],
"category": "资讯",
"worth_keeping": true,
"worth_reason": "该文章清晰记录了 FreshRSS 一个具体版本的更新内容,对用户和开发者具有明确的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
}
File diff suppressed because one or more lines are too long
@@ -0,0 +1,42 @@
{
"candidate_id": "cand:sha256:6b36071bbd22c58692c039e172669ae28ac1ec8a6a6bce150c22d80af29761fc",
"title": "FreshRSS 1.28.0",
"url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.0",
"canonical_url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.0",
"published_at": "2025-12-24T19:27:23Z",
"author": "Alkarex",
"source_name": "FreshRSS releases",
"language": null,
"summary": "FreshRSS 1.28.0 是一个主要版本更新,引入了多项新功能、性能改进和错误修复。更新包括新的排序过滤选项、高级搜索表单、API 功能增强以及 Docker 镜像更新。此版本还包含安全增强、UI 优化和针对大型实例的性能扩展。",
"highlights": [
"新增按用户修改日期排序和过滤功能,支持如 userdate:PT1H 的搜索操作符。",
"改进了对拥有 1000 以上用户的大型实例的统计信息扩展和 SQL 查询速度。",
"Docker 默认镜像已更新至 Debian 13 Trixie 和 PHP 8.4.11。",
"修复了 OpenID Connect 在 Debian 13 上的问题以及 MySQL/MariaDB 的错误排序。",
"将不安全的自动登录功能移至扩展,并对部分扩展存在潜在的破坏性变更。"
],
"keywords": [
"FreshRSS",
"用户修改日期排序",
"高级搜索表单",
"Capy Reader",
"Docker",
"Debian 13 Trixie",
"PHP 8.4.11",
"OpenID Connect"
],
"topics": [
"开源软件",
"RSS 阅读器",
"版本发布",
"软件开发",
"系统维护"
],
"category": "资讯",
"worth_keeping": true,
"worth_reason": "该文章详细记录了 FreshRSS 一个重要版本的功能更新、性能优化和修复内容,对用户和开发者具有明确的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
}
@@ -0,0 +1,224 @@
{
"schema_version": "v1",
"generated_at": "2026-03-26T02:17:31.459980Z",
"run_id": "openclaw-delivery-20260326-021731",
"date": "2026-03-25",
"candidates": [
{
"candidate_id": "cand:sha256:0d315d9489010cfd470a8d479e4e4443722fffdc34ecc1245c1b92458ace5093",
"title": "科技爱好者周刊(第 388 期):测试是新的护城河",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"published_at": "2026-03-12T23:59:16Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "本期讨论了AI快速复刻大型软件的现象,以Cloudflare工程师一周内用AI重写Next.js为例。文章指出,完备的测试用例成为软件公司防止AI复刻的新护城河,并探讨了AI复刻带来的版权问题。",
"highlights": [
"Cloudflare工程师仅用一周和1100美元Token费用,通过AI复刻了Next.js,性能优于原版。",
"软件护城河从代码转向测试用例,例如SQLite的闭源测试套件TH3是其难以复刻的核心。",
"AI复刻软件引发版权争议,如chardet项目因许可证更改产生纠纷,且AI生成物可能无版权。",
"文章列举了多个科技动态,包括AI改写脏话、激光飞机上网、数字分身争议等。",
"周刊还包含工具推荐、资源分享及读者评论,探讨了AI对程序员行业的影响。"
],
"keywords": [
"Next.js",
"AI复刻",
"测试用例",
"SQLite",
"MIT许可证",
"Cloudflare",
"vinext",
"护城河"
],
"topics": [
"人工智能",
"软件开发",
"开源技术",
"科技趋势",
"版权法律"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入分析了AI对软件行业的冲击,提出了测试作为新护城河的见解,具有前瞻性和讨论价值。",
"selection_decision": "review",
"selection_reason": "Article may be behind a paywall.",
"digest_section_hint": null,
"digest_rank": 95
},
{
"candidate_id": "cand:sha256:4139f277b8cb621b02b3398f8a7bd78e3f9eef7bcd320b70b8590e802540c6ca",
"title": "套壳中国大模型撑起500亿美元估值?扒一扒 Cursor 的\"套壳\"疑云",
"url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"published_at": "2026-03-21T10:19:11Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "AI编程工具Cursor推出的Composer 2模型被揭露实为套壳中国模型Kimi K2.5。尽管Cursor通过合作伙伴获得授权未侵权,但其隐瞒行为被认为是为支撑高估值而包装成自研模型公司。事件引发对国产大模型技术输出和信心的讨论。",
"highlights": [
"Cursor的Composer 2模型被技术手段揭露实际请求的模型ID为Kimi K2.5。",
"Cursor通过Fireworks AI获得Kimi授权,未违反许可条款,但刻意隐瞒使用事实。",
"Cursor估值在短期内从数千万美元飙升至数百亿美元,有动机包装自研能力以支撑估值。",
"事件显示中国大模型技术已能对外输出,国产模型与国外旗舰差距正在缩小。",
"Kimi在此事件中获得大量曝光,其下一代K3模型被期待有显著性能提升。"
],
"keywords": [
"Cursor",
"Composer 2",
"Kimi K2.5",
"Fireworks AI",
"模型套壳",
"MIT许可证",
"估值泡沫",
"AI编程工具"
],
"topics": [
"人工智能",
"大模型",
"商业伦理",
"技术授权",
"创业融资"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入剖析了AI行业热点事件,涉及技术真相、商业动机和产业趋势,具有较高的讨论和参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
},
{
"candidate_id": "cand:sha256:a16942c9699333155498d2bc59c530358bd6d81d9afe01e2b96e0e862edfc6a6",
"title": "科技爱好者周刊(第 389 期):未来如何招聘程序员",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"canonical_url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"published_at": "2026-03-19T23:59:16Z",
"author": "阮一峰",
"source_name": "阮一峰的网络日志",
"language": null,
"summary": "本文探讨了在AI编程普及的未来,如何有效招聘程序员。作者认为传统的代码能力考察将不再重要,面试重点应转向考察应聘者使用AI工具、分解项目需求以及系统架构的能力。文章也指出,目前尚难确定一套能可靠筛选合格AI编程人才的面试问题。",
"highlights": [
"未来程序员招聘的核心考察点将从手写代码能力转向熟练运用AI工具的能力。",
"面试问题可能包括如何将复杂需求转化为清晰的提示词,以及设计多Agent协同工作机制。",
"传统的编程语法细节考察意义下降,系统架构知识和项目经验可能仍是重要参考。",
"AI的快速发展使得软件开发流程和人才评估标准面临颠覆性变化。",
"文章还包含科技动态、工具推荐、资源分享等周刊常规栏目内容。"
],
"keywords": [
"AI编程",
"程序员招聘",
"面试问题",
"提示词工程",
"多Agent协同",
"系统架构",
"科技动态",
"工具推荐"
],
"topics": [
"人工智能",
"软件开发",
"职业发展",
"科技资讯",
"效率工具"
],
"category": "观点评论",
"worth_keeping": true,
"worth_reason": "文章深入探讨了AI时代对程序员职业及招聘流程的潜在影响,具有前瞻性和讨论价值,且内容结构完整、信息量丰富。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
},
{
"candidate_id": "cand:sha256:419828361de854cd29dbcd3e8205d3da50ff955ac9c85861d2e195bc888b2103",
"title": "FreshRSS 1.28.1",
"url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.1",
"canonical_url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.1",
"published_at": "2026-01-25T18:20:16Z",
"author": "Alkarex",
"source_name": "FreshRSS releases",
"language": null,
"summary": "FreshRSS 1.28.1 是一个专注于修复错误的版本,主要解决了 1.28.0 版本引入的回归问题。该版本包含少量新功能,如可自定义的注册关闭消息,并进行了性能优化。",
"highlights": [
"此版本主要修复了 1.28.0 版本引入的多个回归错误。",
"新增了可自定义的注册关闭消息和 Apache 访问日志中的用户名记录功能。",
"通过禁用 Ajax 请求中用户标签的文章计数来提升性能。",
"修复了涉及过滤器、标签搜索、RSS/OPML 访问和数据库等多个具体问题。",
"该版本由多位贡献者共同完成,包括新加入的开发者。"
],
"keywords": [
"FreshRSS",
"bug 修复",
"回归问题",
"GReader API",
"HTTP Basic Auth",
"Ajax 请求",
"MySQL",
"MariaDB"
],
"topics": [
"开源软件",
"版本更新",
"RSS 阅读器",
"软件开发",
"性能优化"
],
"category": "资讯",
"worth_keeping": true,
"worth_reason": "该文章清晰记录了 FreshRSS 一个具体版本的更新内容,对用户和开发者具有明确的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
},
{
"candidate_id": "cand:sha256:6b36071bbd22c58692c039e172669ae28ac1ec8a6a6bce150c22d80af29761fc",
"title": "FreshRSS 1.28.0",
"url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.0",
"canonical_url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.0",
"published_at": "2025-12-24T19:27:23Z",
"author": "Alkarex",
"source_name": "FreshRSS releases",
"language": null,
"summary": "FreshRSS 1.28.0 是一个主要版本更新,引入了多项新功能、性能改进和错误修复。更新包括新的排序过滤选项、高级搜索表单、API 功能增强以及 Docker 镜像更新。此版本还包含安全增强、UI 优化和针对大型实例的性能扩展。",
"highlights": [
"新增按用户修改日期排序和过滤功能,支持如 userdate:PT1H 的搜索操作符。",
"改进了对拥有 1000 以上用户的大型实例的统计信息扩展和 SQL 查询速度。",
"Docker 默认镜像已更新至 Debian 13 Trixie 和 PHP 8.4.11。",
"修复了 OpenID Connect 在 Debian 13 上的问题以及 MySQL/MariaDB 的错误排序。",
"将不安全的自动登录功能移至扩展,并对部分扩展存在潜在的破坏性变更。"
],
"keywords": [
"FreshRSS",
"用户修改日期排序",
"高级搜索表单",
"Capy Reader",
"Docker",
"Debian 13 Trixie",
"PHP 8.4.11",
"OpenID Connect"
],
"topics": [
"开源软件",
"RSS 阅读器",
"版本发布",
"软件开发",
"系统维护"
],
"category": "资讯",
"worth_keeping": true,
"worth_reason": "该文章详细记录了 FreshRSS 一个重要版本的功能更新、性能优化和修复内容,对用户和开发者具有明确的参考价值。",
"selection_decision": "review",
"selection_reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"digest_section_hint": null,
"digest_rank": 60
}
],
"stats": {
"total": 5,
"keep_total": 0,
"review_total": 5,
"drop_total": 0
}
}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,32 @@
{
"success": true,
"article": {
"extract_id": "sha256:169f2b50eec3d198df126a8daedb95c48cff252ead9d4d2598a449e128cae2b8",
"item_id": "sha256:419828361de854cd29dbcd3e8205d3da50ff955ac9c85861d2e195bc888b2103",
"source_id": "freshrss:2987af960359c5c0",
"url": "https://github.com/FreshRSS/FreshRSS/releases/tag/1.28.1",
"title": "FreshRSS 1.28.1",
"author": "Alkarex",
"published_at": "2026-01-25T18:20:16Z",
"language": null,
"content_kind": "article",
"plain_text": "Alkarex\nreleased this\n25 Jan 18:20\n·\n79 commits\nto edge\nsince this release\nImmutable\nrelease. Only release title and notes can be modified.\nThis is a release focussing on bug fixing, in particular regressions from the release 1.28.0.\nSelected new features ✨:\n- New customisable message for closed registrations\n- Add username in Apache access logs (also in Docker logs): for GReader API, and for HTTP Basic Auth from reverse proxy\nImproved performance 🏎️:\n- Disable counting articles in user labels for Ajax requests (unused)\nMany bug fixes 🐛\nThis release has been made by @Alkarex, @Frenzie, @Inverle and newcomers @ciro-mota, @eveiscoull, @hackerman70000, @Hufschmidt, @johan456789, @martgnz, @mmeier86, @netsho, @neuhaus, @RobLoach, @rupakbajgain.\nFull changelog:\n- Features\n- Bug fixing\n- Fix unwanted expansion of user queries (saved searches) applied to filters #8395\n- Fix encoding of filter actions for labels #8368\n- Fix searching of tags #8425\n- Fix refreshing feeds with token while anonymous refresh is disabled #8371\n- Fix RSS and OPML access by token #8434\n- Fix MySQL/MariaDB\ntransliterator_transliterate\nfallback (when thephp-intl\nextension is unavailable) #8427 - Fix regression with MySQL/MariaDB index hint #8460\n- Auto-add\nlastUserModified\ndatabase column also during mark-as-read action #8346 - Do not include hidden feeds when counting unread articles in categories #8357\n- Remove wrong PHP deprecation of OPML export action #8399\n- Fix shortcut for next unread article #8466\n- Fix custom\nsession.cookie-lifetime\n#8446 - Fix feed validator button when changing the feed URL #8436\n- Performance\n- Disable counting articles in user labels for Ajax requests (unused) #8352\n- Security\n- Deployment\n- Add username in Apache access logs (also in Docker logs): for GReader API, and for HTTP Basic Auth from reverse proxy #8392\n- SimplePie\n- Update of\nCURLOPT_ACCEPT_ENCODING\n#8376, simplepie#960, simplepie#962 - Fix don’t preserve children inside disallowed\n<template>\nelement #8443 - Fixes before PHPStan 2 #8445, simplepie#957\n- Update of\n- Extensions\n- Update\n.gitignore\nto ignore installed extensions #8372\n- Update\n- UI\n- I18n\n- Misc.",
"quality_flags": {
"is_paywalled": false,
"is_truncated": false,
"is_low_content": false
},
"metadata": {
"content_source": "fetched_html",
"extractor": "trafilatura",
"char_count": 2155
},
"pipeline_state": "extracted"
},
"error": null,
"debug": {
"content_source": "fetched_html",
"extractor": "trafilatura"
},
"warnings": []
}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,26 @@
{
"decision": "review",
"matched_rules": [
"review-worth-keeping-other"
],
"reasons": [
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"summary"
],
"priority": 60,
"matches": [
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
@@ -0,0 +1,26 @@
{
"decision": "review",
"matched_rules": [
"review-worth-keeping-other"
],
"reasons": [
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"summary"
],
"priority": 60,
"matches": [
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
@@ -0,0 +1,40 @@
{
"decision": "review",
"matched_rules": [
"review-paywalled-content",
"review-worth-keeping-other"
],
"reasons": [
"Article may be behind a paywall.",
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"paywall",
"quality",
"summary"
],
"priority": 95,
"matches": [
{
"rule_id": "review-paywalled-content",
"decision": "review",
"reason": "Article may be behind a paywall.",
"labels": [
"quality",
"paywall"
],
"priority": 95
},
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
@@ -0,0 +1,26 @@
{
"decision": "review",
"matched_rules": [
"review-worth-keeping-other"
],
"reasons": [
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"summary"
],
"priority": 60,
"matches": [
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
@@ -0,0 +1,26 @@
{
"decision": "review",
"matched_rules": [
"review-worth-keeping-other"
],
"reasons": [
"Worth-keeping signal is positive but no stronger keep rule matched."
],
"labels": [
"needs-review",
"summary"
],
"priority": 60,
"matches": [
{
"rule_id": "review-worth-keeping-other",
"decision": "review",
"reason": "Worth-keeping signal is positive but no stronger keep rule matched.",
"labels": [
"summary",
"needs-review"
],
"priority": 60
}
]
}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,32 @@
{
"title": "套壳中国大模型撑起500亿美元估值?扒一扒 Cursor 的\"套壳\"疑云",
"url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"summary": "AI编程工具Cursor推出的Composer 2模型被揭露实为套壳中国模型Kimi K2.5。尽管Cursor通过合作伙伴获得授权未侵权,但其隐瞒行为被认为是为支撑高估值而包装成自研模型公司。事件引发对国产大模型技术输出和信心的讨论。",
"highlights": [
"Cursor的Composer 2模型被技术手段揭露实际请求的模型ID为Kimi K2.5。",
"Cursor通过Fireworks AI获得Kimi授权,未违反许可条款,但刻意隐瞒使用事实。",
"Cursor估值在短期内从数千万美元飙升至数百亿美元,有动机包装自研能力以支撑估值。",
"事件显示中国大模型技术已能对外输出,国产模型与国外旗舰差距正在缩小。",
"Kimi在此事件中获得大量曝光,其下一代K3模型被期待有显著性能提升。"
],
"keywords": [
"Cursor",
"Composer 2",
"Kimi K2.5",
"Fireworks AI",
"模型套壳",
"MIT许可证",
"估值泡沫",
"AI编程工具"
],
"topics": [
"人工智能",
"大模型",
"商业伦理",
"技术授权",
"创业融资"
],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入剖析了AI行业热点事件,涉及技术真相、商业动机和产业趋势,具有较高的讨论和参考价值。"
}
@@ -0,0 +1,11 @@
{
"title": "套壳中国大模型撑起500亿美元估值?扒一扒 Cursor 的\"套壳\"疑云",
"url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"summary": "AI编程工具Cursor推出的Composer 2模型被揭露实为套壳中国模型Kimi K2.5。尽管Cursor通过合作伙伴获得授权未侵权,但其隐瞒行为被认为是为支撑高估值而包装成自研模型公司。事件引发对国产大模型技术输出和信心的讨论。",
"highlights": ["Cursor的Composer 2模型被技术手段揭露实际请求的模型ID为Kimi K2.5。", "Cursor通过Fireworks AI获得Kimi授权,未违反许可条款,但刻意隐瞒使用事实。", "Cursor估值在短期内从数千万美元飙升至数百亿美元,有动机包装自研能力以支撑估值。", "事件显示中国大模型技术已能对外输出,国产模型与国外旗舰差距正在缩小。", "Kimi在此事件中获得大量曝光,其下一代K3模型被期待有显著性能提升。"],
"keywords": ["Cursor", "Composer 2", "Kimi K2.5", "Fireworks AI", "模型套壳", "MIT许可证", "估值泡沫", "AI编程工具"],
"topics": ["人工智能", "大模型", "商业伦理", "技术授权", "创业融资"],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入剖析了AI行业热点事件,涉及技术真相、商业动机和产业趋势,具有较高的讨论和参考价值。"
}
@@ -0,0 +1,37 @@
{
"valid": true,
"errors": [],
"warnings": [],
"normalized_result": {
"title": "套壳中国大模型撑起500亿美元估值?扒一扒 Cursor 的\"套壳\"疑云",
"url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"summary": "AI编程工具Cursor推出的Composer 2模型被揭露实为套壳中国模型Kimi K2.5。尽管Cursor通过合作伙伴获得授权未侵权,但其隐瞒行为被认为是为支撑高估值而包装成自研模型公司。事件引发对国产大模型技术输出和信心的讨论。",
"highlights": [
"Cursor的Composer 2模型被技术手段揭露实际请求的模型ID为Kimi K2.5。",
"Cursor通过Fireworks AI获得Kimi授权,未违反许可条款,但刻意隐瞒使用事实。",
"Cursor估值在短期内从数千万美元飙升至数百亿美元,有动机包装自研能力以支撑估值。",
"事件显示中国大模型技术已能对外输出,国产模型与国外旗舰差距正在缩小。",
"Kimi在此事件中获得大量曝光,其下一代K3模型被期待有显著性能提升。"
],
"keywords": [
"Cursor",
"Composer 2",
"Kimi K2.5",
"Fireworks AI",
"模型套壳",
"MIT许可证",
"估值泡沫",
"AI编程工具"
],
"topics": [
"人工智能",
"大模型",
"商业伦理",
"技术授权",
"创业融资"
],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入剖析了AI行业热点事件,涉及技术真相、商业动机和产业趋势,具有较高的讨论和参考价值。"
}
}
@@ -0,0 +1,32 @@
{
"title": "套壳中国大模型撑起500亿美元估值?扒一扒 Cursor 的\"套壳\"疑云",
"url": "http://www.ruanyifeng.com/blog/2026/03/kimi-cursor.html",
"summary": "AI编程工具Cursor推出的Composer 2模型被揭露实为套壳中国模型Kimi K2.5。尽管Cursor通过合作伙伴获得授权未侵权,但其隐瞒行为被认为是为支撑高估值而包装成自研模型公司。事件引发对国产大模型技术输出和信心的讨论。",
"highlights": [
"Cursor的Composer 2模型被技术手段揭露实际请求的模型ID为Kimi K2.5。",
"Cursor通过Fireworks AI获得Kimi授权,未违反许可条款,但刻意隐瞒使用事实。",
"Cursor估值在短期内从数千万美元飙升至数百亿美元,有动机包装自研能力以支撑估值。",
"事件显示中国大模型技术已能对外输出,国产模型与国外旗舰差距正在缩小。",
"Kimi在此事件中获得大量曝光,其下一代K3模型被期待有显著性能提升。"
],
"keywords": [
"Cursor",
"Composer 2",
"Kimi K2.5",
"Fireworks AI",
"模型套壳",
"MIT许可证",
"估值泡沫",
"AI编程工具"
],
"topics": [
"人工智能",
"大模型",
"商业伦理",
"技术授权",
"创业融资"
],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入剖析了AI行业热点事件,涉及技术真相、商业动机和产业趋势,具有较高的讨论和参考价值。"
}
@@ -0,0 +1,32 @@
{
"title": "科技爱好者周刊(第 389 期):未来如何招聘程序员",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"summary": "本文探讨了在AI编程普及的未来,如何有效招聘程序员。作者认为传统的代码能力考察将不再重要,面试重点应转向考察应聘者使用AI工具、分解项目需求以及系统架构的能力。文章也指出,目前尚难确定一套能可靠筛选合格AI编程人才的面试问题。",
"highlights": [
"未来程序员招聘的核心考察点将从手写代码能力转向熟练运用AI工具的能力。",
"面试问题可能包括如何将复杂需求转化为清晰的提示词,以及设计多Agent协同工作机制。",
"传统的编程语法细节考察意义下降,系统架构知识和项目经验可能仍是重要参考。",
"AI的快速发展使得软件开发流程和人才评估标准面临颠覆性变化。",
"文章还包含科技动态、工具推荐、资源分享等周刊常规栏目内容。"
],
"keywords": [
"AI编程",
"程序员招聘",
"面试问题",
"提示词工程",
"多Agent协同",
"系统架构",
"科技动态",
"工具推荐"
],
"topics": [
"人工智能",
"软件开发",
"职业发展",
"科技资讯",
"效率工具"
],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入探讨了AI时代对程序员职业及招聘流程的潜在影响,具有前瞻性和讨论价值,且内容结构完整、信息量丰富。"
}
@@ -0,0 +1,19 @@
```json
{
"title": "科技爱好者周刊(第 389 期):未来如何招聘程序员",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"summary": "本文探讨了在AI编程普及的未来,如何有效招聘程序员。作者认为传统的代码能力考察将不再重要,面试重点应转向考察应聘者使用AI工具、分解项目需求以及系统架构的能力。文章也指出,目前尚难确定一套能可靠筛选合格AI编程人才的面试问题。",
"highlights": [
"未来程序员招聘的核心考察点将从手写代码能力转向熟练运用AI工具的能力。",
"面试问题可能包括如何将复杂需求转化为清晰的提示词,以及设计多Agent协同工作机制。",
"传统的编程语法细节考察意义下降,系统架构知识和项目经验可能仍是重要参考。",
"AI的快速发展使得软件开发流程和人才评估标准面临颠覆性变化。",
"文章还包含科技动态、工具推荐、资源分享等周刊常规栏目内容。"
],
"keywords": ["AI编程", "程序员招聘", "面试问题", "提示词工程", "多Agent协同", "系统架构", "科技动态", "工具推荐"],
"topics": ["人工智能", "软件开发", "职业发展", "科技资讯", "效率工具"],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入探讨了AI时代对程序员职业及招聘流程的潜在影响,具有前瞻性和讨论价值,且内容结构完整、信息量丰富。"
}
```
@@ -0,0 +1,37 @@
{
"valid": true,
"errors": [],
"warnings": [],
"normalized_result": {
"title": "科技爱好者周刊(第 389 期):未来如何招聘程序员",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"summary": "本文探讨了在AI编程普及的未来,如何有效招聘程序员。作者认为传统的代码能力考察将不再重要,面试重点应转向考察应聘者使用AI工具、分解项目需求以及系统架构的能力。文章也指出,目前尚难确定一套能可靠筛选合格AI编程人才的面试问题。",
"highlights": [
"未来程序员招聘的核心考察点将从手写代码能力转向熟练运用AI工具的能力。",
"面试问题可能包括如何将复杂需求转化为清晰的提示词,以及设计多Agent协同工作机制。",
"传统的编程语法细节考察意义下降,系统架构知识和项目经验可能仍是重要参考。",
"AI的快速发展使得软件开发流程和人才评估标准面临颠覆性变化。",
"文章还包含科技动态、工具推荐、资源分享等周刊常规栏目内容。"
],
"keywords": [
"AI编程",
"程序员招聘",
"面试问题",
"提示词工程",
"多Agent协同",
"系统架构",
"科技动态",
"工具推荐"
],
"topics": [
"人工智能",
"软件开发",
"职业发展",
"科技资讯",
"效率工具"
],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入探讨了AI时代对程序员职业及招聘流程的潜在影响,具有前瞻性和讨论价值,且内容结构完整、信息量丰富。"
}
}
@@ -0,0 +1,32 @@
{
"title": "科技爱好者周刊(第 389 期):未来如何招聘程序员",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-389.html",
"summary": "本文探讨了在AI编程普及的未来,如何有效招聘程序员。作者认为传统的代码能力考察将不再重要,面试重点应转向考察应聘者使用AI工具、分解项目需求以及系统架构的能力。文章也指出,目前尚难确定一套能可靠筛选合格AI编程人才的面试问题。",
"highlights": [
"未来程序员招聘的核心考察点将从手写代码能力转向熟练运用AI工具的能力。",
"面试问题可能包括如何将复杂需求转化为清晰的提示词,以及设计多Agent协同工作机制。",
"传统的编程语法细节考察意义下降,系统架构知识和项目经验可能仍是重要参考。",
"AI的快速发展使得软件开发流程和人才评估标准面临颠覆性变化。",
"文章还包含科技动态、工具推荐、资源分享等周刊常规栏目内容。"
],
"keywords": [
"AI编程",
"程序员招聘",
"面试问题",
"提示词工程",
"多Agent协同",
"系统架构",
"科技动态",
"工具推荐"
],
"topics": [
"人工智能",
"软件开发",
"职业发展",
"科技资讯",
"效率工具"
],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入探讨了AI时代对程序员职业及招聘流程的潜在影响,具有前瞻性和讨论价值,且内容结构完整、信息量丰富。"
}
@@ -0,0 +1,32 @@
{
"title": "科技爱好者周刊(第 388 期):测试是新的护城河",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"summary": "本期讨论了AI快速复刻大型软件的现象,以Cloudflare工程师一周内用AI重写Next.js为例。文章指出,完备的测试用例成为软件公司防止AI复刻的新护城河,并探讨了AI复刻带来的版权问题。",
"highlights": [
"Cloudflare工程师仅用一周和1100美元Token费用,通过AI复刻了Next.js,性能优于原版。",
"软件护城河从代码转向测试用例,例如SQLite的闭源测试套件TH3是其难以复刻的核心。",
"AI复刻软件引发版权争议,如chardet项目因许可证更改产生纠纷,且AI生成物可能无版权。",
"文章列举了多个科技动态,包括AI改写脏话、激光飞机上网、数字分身争议等。",
"周刊还包含工具推荐、资源分享及读者评论,探讨了AI对程序员行业的影响。"
],
"keywords": [
"Next.js",
"AI复刻",
"测试用例",
"SQLite",
"MIT许可证",
"Cloudflare",
"vinext",
"护城河"
],
"topics": [
"人工智能",
"软件开发",
"开源技术",
"科技趋势",
"版权法律"
],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入分析了AI对软件行业的冲击,提出了测试作为新护城河的见解,具有前瞻性和讨论价值。"
}
@@ -0,0 +1,11 @@
{
"title": "科技爱好者周刊(第 388 期):测试是新的护城河",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"summary": "本期讨论了AI快速复刻大型软件的现象,以Cloudflare工程师一周内用AI重写Next.js为例。文章指出,完备的测试用例成为软件公司防止AI复刻的新护城河,并探讨了AI复刻带来的版权问题。",
"highlights": ["Cloudflare工程师仅用一周和1100美元Token费用,通过AI复刻了Next.js,性能优于原版。", "软件护城河从代码转向测试用例,例如SQLite的闭源测试套件TH3是其难以复刻的核心。", "AI复刻软件引发版权争议,如chardet项目因许可证更改产生纠纷,且AI生成物可能无版权。", "文章列举了多个科技动态,包括AI改写脏话、激光飞机上网、数字分身争议等。", "周刊还包含工具推荐、资源分享及读者评论,探讨了AI对程序员行业的影响。"],
"keywords": ["Next.js", "AI复刻", "测试用例", "SQLite", "MIT许可证", "Cloudflare", "vinext", "护城河"],
"topics": ["人工智能", "软件开发", "开源技术", "科技趋势", "版权法律"],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入分析了AI对软件行业的冲击,提出了测试作为新护城河的见解,具有前瞻性和讨论价值。"
}
@@ -0,0 +1,37 @@
{
"valid": true,
"errors": [],
"warnings": [],
"normalized_result": {
"title": "科技爱好者周刊(第 388 期):测试是新的护城河",
"url": "http://www.ruanyifeng.com/blog/2026/03/weekly-issue-388.html",
"summary": "本期讨论了AI快速复刻大型软件的现象,以Cloudflare工程师一周内用AI重写Next.js为例。文章指出,完备的测试用例成为软件公司防止AI复刻的新护城河,并探讨了AI复刻带来的版权问题。",
"highlights": [
"Cloudflare工程师仅用一周和1100美元Token费用,通过AI复刻了Next.js,性能优于原版。",
"软件护城河从代码转向测试用例,例如SQLite的闭源测试套件TH3是其难以复刻的核心。",
"AI复刻软件引发版权争议,如chardet项目因许可证更改产生纠纷,且AI生成物可能无版权。",
"文章列举了多个科技动态,包括AI改写脏话、激光飞机上网、数字分身争议等。",
"周刊还包含工具推荐、资源分享及读者评论,探讨了AI对程序员行业的影响。"
],
"keywords": [
"Next.js",
"AI复刻",
"测试用例",
"SQLite",
"MIT许可证",
"Cloudflare",
"vinext",
"护城河"
],
"topics": [
"人工智能",
"软件开发",
"开源技术",
"科技趋势",
"版权法律"
],
"category": "观点评论",
"worth_keeping": true,
"reason": "文章深入分析了AI对软件行业的冲击,提出了测试作为新护城河的见解,具有前瞻性和讨论价值。"
}
}

Some files were not shown because too many files have changed in this diff Show More